以下是最简单的示例,尽管任何解决方案都应能够扩展到需要n个顶级结果的地方:
给定下面的表格,其中包含“人员”,“组”和“年龄”列,您将如何 获得每个组中 年龄 最大的2个人? (组内的关系不应产生更多结果,而应按字母顺序给出前两个)
+ -------- + ------- + ----- + | 人 集团| 年龄| + -------- + ------- + ----- + | 鲍勃| 1 | 32 | | 吉尔| 1 | 34 | | 肖恩| 1 | 42 | | 杰克 2 | 29 | | 保罗| 2 | 36 | | 劳拉| 2 | 39 | + -------- + ------- + ----- +
所需的结果集:
+ -------- + ------- + ----- + | 肖恩| 1 | 42 | | 吉尔| 1 | 34 | | 劳拉| 2 | 39 | | 保罗| 2 | 36 | + -------- + ------- + ----- +
注意: 这个问题建立在先前的问题上- 获取每组分组的SQL结果的最大值的记录 -用于从每组中获取一个顶行,并且从@Bohemian那里收到了一个MySQL特有的答案:
select * from (select * from mytable order by `Group`, Age desc, Person) x group by `Group`
我希望能够以此为基础,尽管我不知道如何做到。
这是使用的一种方法UNION ALL(请参阅带有演示的SQL Fiddle)。这适用于两个组,如果您有两个以上的组,则需要指定group数字并为每个组添加查询group:
UNION ALL
group
( select * from mytable where `group` = 1 order by age desc LIMIT 2 ) UNION ALL ( select * from mytable where `group` = 2 order by age desc LIMIT 2 )
有多种方法可以执行此操作,请参阅本文以确定适合您情况的最佳路线:
http://www.xaprb.com/blog/2006/12/07/how-to-select-the-firstleastmax-row-per- group-in-sql/
编辑:
这也可能对您有用,它会为每个记录生成一个行号。使用上面链接中的示例,这将仅返回行号小于或等于2的那些记录:
select person, `group`, age from ( select person, `group`, age, (@num:=if(@group = `group`, @num +1, if(@group := `group`, 1, 1))) row_number from test t CROSS JOIN (select @num:=0, @group:=null) c order by `Group`, Age desc, person ) as x where x.row_number <= 2;
观看演示