我有一个简单的表User
,其中包含两个属性ID
和AGE
现在我希望在AGE
User Table
ID AGE
0 23
1 35
2 30
3 52
4 35
5 23
6 19
如果我select * from User order by AGE ASC
我可以轻松获得如下排序结果:
ID AGE
6 19
0 23
5 23
2 30
1 35
4 35
3 52
但我真正想要的是:
ID RANK
6 0
0 1
5 1
2 3
1 4
4 4
3 6
我在下面提出了相当不错的解决方案,但它有一个很小的缺陷
SELECT U1.ID, count(*) AS RANK
FROM User U1, User U2
WHERE U1.age > U2.age
GROUP BY U1.ID ORDER BY RANK;
这给了我:
ID RANK
0 1
5 1
2 3
1 4
4 4
3 6
这是正确的,除了我失去一个排名为零的原因WHERE U1.age > U2.age
对于最年轻的用户来说永远不会是真的。
请提前感谢这个问题!
答案 0 :(得分:2)
不幸的是,MySQL仍然缺乏对分析功能的支持。在MySQL中模拟RANK()
的一种方法
SELECT id, rank
FROM
(
SELECT id, @n := @n + 1, @r := IF(@a = age, @r, @n) rank, @a := age
FROM user CROSS JOIN (SELECT @n := -1, @r := -1, @a := NULL) i
ORDER BY age
) q
输出:
| ID | RANK | |----|------| | 6 | 0 | | 0 | 1 | | 5 | 1 | | 2 | 3 | | 1 | 4 | | 4 | 4 | | 3 | 6 |
这是 SQLFiddle 演示
你应该在你的问题中告诉你,你实际上首先使用的是Postgres。'
不幸的是@ t-clausen.dk删除了他的回答,根据您发现的使用支持分析功能的Postgres的事实,这个回答绝对正确
SELECT ID, RANK() OVER (ORDER BY age) - 1 rank
FROM "user"
这是最好的方式。
这是 SQLFiddle 演示
答案 1 :(得分:1)
SELECT t1.id,
(SELECT COUNT(*) FROM User t2 WHERE t2.AGE < t1.AGE)
AS rnk
FROM User t1 order by rnk ;
<强> Sample fiddle 强>