MYSQL UNION ORDER BY - php

I currently have this
SELECT *
FROM images
WHERE images.id IN (SELECT image_id FROM image_likes WHERE user_id = '1')
UNION
SELECT *
FROM images
WHERE images.user_id = '1' AND upload_type in (4,3) ORDER BY id DESC
And this works great, but now i want it to display the most recent results thats have happend.
For example, User A uploaded a image-> information goes into images with a timestamp. User A then likes someone else's image -> Information goes into image_likes with a timestamp. Now how would i make the two timestamp column's merge together so i can sort them by DESC.
Breif run over of what the query does.
Selects the image information from images where the user has liked a image in image_likes and then it grabs all of the uploads the user has uploaded from images and merges them into a query. What i need is to be able to sort them using the timestamp from both tables.

how about doing this??
SELECT * FROM (
SELECT *
FROM images
WHERE images.id IN (SELECT image_id FROM image_likes WHERE user_id = '1')
UNION
SELECT *
FROM images
WHERE images.user_id = '1' AND upload_type in (4,3) ORDER BY id DESC
) AS a ORDER BY a.timestamp DESC;
OR even better
(SELECT *
FROM images
WHERE images.id IN (SELECT image_id FROM image_likes WHERE user_id = '1'))
UNION
(SELECT *
FROM images
WHERE images.user_id = '1' AND upload_type in (4,3) ORDER BY id DESC)
ORDER BY timestamp DESC
chk this http://dev.mysql.com/doc/refman/5.5/en/union.html
UPDATE
TRY THIS
(SELECT images.id, images_likes.timestamp as timestamp FROM images JOIN images_likes
ON images.id=image_likes.image_id WHERE user_id = '1')
UNION
(SELECT images.id, images.timestamp as timestamp
FROM images
WHERE images.user_id = '1' AND upload_type in (4,3) ORDER BY id DESC)
ORDER BY timestamp DESC
UPDATE
Final query as per your requirement
(SELECT images.id, images.user_id, images.ext, images.upload_type, images_likes.timestamp as timestamp FROM images JOIN images_likes
ON images.id=image_likes.image_id WHERE images_likes.user_id = '1')
UNION
(SELECT images.id, images.user_id, images.ext, images.upload_type, images.timestamp as timestamp
FROM images
WHERE images.user_id = '1' AND upload_type in (4,3) ORDER BY id DESC)
ORDER BY timestamp DESC

I would approach with the following... The "PreQuery" below starts with all images the user likes first, with the max timestamp as a new column "MostRecent". THEN, do a UNION ALL for the next set. The next set is directly from the images table for the user, but LEFT JOINED to the "Liked" images. Then the WHERE clause explicitly excludes those that would have been returned in the first set by using the "iml2.image_id IS NULL". I did this as I wasn't positive on how the union would handle the group by in the first set, but no group by in the second. Ex: If the image was created with date/timestamp of say Mar 3, but also found as a "Like" of Mar 5, I didn't want one instance listed as each distinct date (as union already qualifies distinct implied).
That said, I will have a single prequery result of any image the person liked with its most recent date/time stamp, AND all their own personal images with their respective date/time stamp. Now, its a simple join back to the images table to grab the details (via alias "i2") and we can sort by the PreQuery.MostRecent column, then by the image ID value descending.
SELECT
i2.*
from
( select iml.image_id as id,
max( iml.YourTimeStamp ) as MostRecent
from image_likes iml
where iml.user_id = '1'
group by iml.image_id
UNION ALL
select i.id,
i.ImageTimeStamp as MostRecent
from images i
left join image_likes iml2
on i.id = iml2.image_id
and iml2.user_id = '1'
where i.user_id = '1'
and i.upload_type in ( 4, 3 )
and iml2.image_id is null
) PreQuery
JOIN Images i2
on PreQuery.id = i2.id
order by
PreQuery.MostRecent,
PreQuery.ID desc

Why don't you use a 'OR'?
that way :
SELECT *
FROM images
WHERE images.id IN (SELECT image_id FROM image_likes WHERE user_id = '1')
OR (images.user_id = '1' AND upload_type in (4,3))
ORDER BY id DESC

SELECT *
FROM
( SELECT im.*
, li.timestamp AS ts
FROM images AS im
JOIN image_likes AS li
ON li.image_id = im.image_id
WHERE li.user_id = 1
UNION ALL
SELECT *
, timestamp AS ts
FROM images
WHERE user_id = 1
AND upload_type in (4,3)
) AS tmp
ORDER BY ts DESC

Related

How to order table in mysql by likes relative to their time?

I have simple problem, 2 mysql tables, one holds photos and the other one likes. Structure is like this:
table `photos` - id, name, image_id
table `likes` - id_photos, timestamp
Now it's trivial to order photos by their likes and get TOP 3 like this:
SELECT photos.*
, COUNT(likes.id) AS likes_count
FROM photos
LEFT JOIN likes ON photos.id = likes.id_photos
GROUP BY photos.id
ORDER BY likes_count DESC LIMIT 3;
But what I want to add is time relativity, meaning, that newer likes have more "weight" and even though some photos might have more likes, their are older and they order lower than photos with fewer likes but newer ones.
Is it possible to solve this problem only in MySQL ? Or with additional processing in PHP ?
Let consider case then likes.timestamp is UNIXTIME field, so if we use SUM(timestamp) instead count the new lakes will have more weight :
SELECT photos.*
, COUNT(likes.id) AS likes_count
, SUM(likes.timestamp) AS likes_weight
FROM photos
LEFT JOIN likes ON photos.id = likes.id_photos
GROUP BY photos.id
ORDER BY likes_weight DESC LIMIT 3;
Possible to use some coefficient (for example UNIX_TIMESTAMP())
SELECT photos.*
, COUNT(likes.id) AS likes_count
, SUM(likes.timestamp)/UNIX_TIMESTAMP() AS likes_weight
FROM photos
LEFT JOIN likes ON photos.id = likes.id_photos
GROUP BY photos.id
ORDER BY likes_weight DESC LIMIT 3;

MySQL - GROUP BY with ORDER DESC not working

Hi I am having a problem with following query.
SELECT id, user_id, cloth_id FROM `items` GROUP BY user_id ORDER BY id desc LIMIT 3
I want the latest records with group by but somehow its showing old records.
I have also gone through MySQL - Group by with Order by DESC but not working as expected.
Try this:
SELECT i.id, i.user_id, i.cloth_id FROM
(
SELECT max(id) as id, user_id FROM `items` GROUP BY user_id
) temp
LEFT JOIN `items` i on i.user_id = temp.user_id AND i.id = temp.id
in temp you get each user with the latest id.
in i you get the cloth_id for that combination

Mysql - get last post from category

I have this structure (tables) of forum
I want to select last post (row from forum_post table) from category.
SQL so far:
SELECT * FROM table_post
WHERE topic_id = (SELECT MAX(id) FROM table_topic WHERE category_id = {$id})
ORDER BY id ASC LIMIT 1
Question: How to modify this select to achieve my goal?
Assuming that "last" means the biggest id, I would suggest order by and limit:
select fp.*
from forum_post fp join
forum_topic ft
on fp.topic_id = ft.id
where ft.category_id = $id
order by fp.id desc
limit 1;

Returning the last two set of records mySQL

well, i'm new to MySQL Database and i got a problem, i need to get the last two set of records from a table ( the records are automatically added to this table every week) i need to use to find the growth that an entity did during the last week.
can any one help plz.
here is what i wrote, i tested it on my local host and it worked :D, but when we installed it online, it crashed :(
select pages.*, new.* from (
select id, tableone.page_id, one, two,(two - one) as diff from
(SELECT id, page_id, likes as two FROM `page_records` WHERE id IN ( SELECT max( id ) FROM `page_records` GROUP BY page_id )) as tableone left join
(SELECT page_id , likes as one FROM `page_records` where id in ( SELECT max(id) FROM `page_records` where id not in (select max(id) from `page_records` group by page_id) group by page_id))
as tabletwo
on tableone.page_id = tabletwo.page_id
order by tableone.page_id asc) as new inner join pages on pages.id = new.page_id
Thanks in advance.
try:
SELECT id, page_id, likes FROM page_records order by id desc limit 0, 2
Try this:
SELECT * FROM table_name
ORDER BY id DESC
LIMIT 0, 2
Thanks!

Select from 2 tables and order by 1

I have 2 tables.
First:
TABLE Articles
ID
Second:
TABLE Viewcount
DATE DATE PK
ARTICLE_ID INT PK (MATCHES ID IN TABLE Articles)
NUMVIEWS INT
How do I select all IDs from table Articles and then order by NUMVIEWS (DESC) of Viewcount according to dates?
I then need to append the IDs from Articles that were not found in viewcount to the End of the results in no particular order.
I know it has to be some sort of Join but I can't figure it out..
try this
SELECT id from Articles a
LEFT JOIN Viewcount v
ON a.id = v.article_id
AND v.date = 'some date here'
ORDER BY v.numviews ,v.date desc
A simple join will suffice, yes:
SELECT a.id FROm Articles a LEFT JOIN Viewcount v
ON v.article_id = a.id
ORDER BY v.numviews desc, v.date
This should work:
SELECT * FROM `Articles` `a`, `Viewcount` `v`
WHERE `v`.`ARTICLE_ID`=`a`.`ID`
ORDER BY `v`.`NUMVIEWS` DESC
Replace SELECT * by SELECT `a`.`ID` to get only the Article IDs.
SELECT ID from (Articles JOIN Viewcount on Articles.ID = Viewcount.ID) ORDER BY Viewcount.NUMVIEWS, Viewcount.date

Categories