限制每个组的查询

时间:2013-02-18 03:13:55

标签: mysql select greatest-n-per-group

我有这个问题:

select pl.photo_id, pl.user_id, pl.liker_id, p1.filename user_filename, p2.filename liker_filename 
FROM photo_likes pl 
 left join photos p1 on (pl.photo_id = p1.photo_id) 
 left join photos p2 on (pl.liker_id = p2.user_id and p2.avatar = 1)
where pl.user_id = $id order by pl.liker_id, pl.date_liked desc

它获取了正确的数据,但我想修改它以限制数据。所以,在一个坚果壳中,这个查询将获得所有喜欢他们的照片的人的所有喜欢,它工作得很好,这可以为每个人抓取很多照片。但是我想限制每个人只有5个:

所以,说user A喜欢我的10张照片,user B喜欢我的8张照片,而user C喜欢我的2张照片,我只想要来自{{1来自user A的最后5个,user B的最后2个。如果这是有道理的,怎么办呢?

2 个答案:

答案 0 :(得分:1)

你的查询是好的,但我正在包装它并使用MySQL变量检查每个返回变量并增加每个“liker”的序列。当liker改变时,将序列设置回1 ....然后,应用HAVING< 6为序列。你不能在WHERE子句中这样做,因为你希望每条记录都是QUALIFIED,它不断更新@likeSeq和@lastLiker。只有在完成之后,HAVING说......在那之后,如果seq大于你的5个上限,它就会抛出它。

每个打印屏幕都包含备用行...

select
      AllRanks.*
   from 
      ( select
                PreQualified.*,
                @likeSeq := if( PreQualified.Liker_ID = @lastLiker, @likeSeq +1, 1 ) as Seq,
                @lastLiker := PreQualified.Liker_ID
             from
                ( select 
                        pl.photo_id, 
                        pl.user_id, 
                        pl.liker_id, 
                        p1.filename user_filename, 
                        p2.filename liker_filename 
                     FROM 
                        photo_likes pl 
                           left join photos p1 
                              on pl.photo_id = p1.photo_id
                           left join photos p2 
                              on pl.liker_id = p2.user_id 
                             and p2.avatar = 1
                     where 
                        pl.user_id = $id 
                     order by 
                        pl.liker_id, 
                        pl.date_liked desc ) PreQualified,
                ( select @lastLiker := 0,
                         @likeSeq := 0 ) sqlvars
      ) AllRanks
   where
      AllRanks.Seq < 6

答案 1 :(得分:0)

您可以将已连接的表包装在子查询中吗?

select ...
from photo_likes
left join photos p1 ...
left join (select p2.filename liker_filename from photos where p1.liker_id = p2.user_id and avatar = 1 LIMIT 5) p2
where ...