我想做一个排名,把最好的5分球员加起来,放在一个排名。球员的得分不超过5分。
目前我有以下疑问:
set @count:=0, @player:='';
SELECT SEIZOEN
, WEDSTRIJDTYPE
, ATLEET_ID
, GROEP_NAAM
, GROEP_OMS
, SUM(PUNTEN_WC) as WC_RESULT
FROM
( SELECT ATLEET_ID
, PUNTEN_WC
, SEIZOEN
, WEDSTRIJDTYPE
, GROEP_NAAM
, GROEP_OMS
FROM
( SELECT PUNTEN_WC
, SEIZOEN
, WEDSTRIJDTYPE
, GROEP_NAAM
, GROEP_OMS
, @count := if (@player != ATLEET_ID,0,@count + 1) as count
, @player := ATLEET_ID as ATLEET_ID
FROM
( SELECT ATLEET_ID
, PUNTEN_WC
, k.SEIZOEN
, k.WEDSTRIJDTYPE
, g.GROEP_NAAM
, g.GROEP_OMS
FROM RESULTATEN r
LEFT
JOIN KALENDER k
ON r.KALENDER_ID = k.KALENDER_ID
JOIN GROEP_SNB g
ON r.GROEP_NAAM = g.GROEP_NAAM
JOIN SKIER s
ON r.ATLEET_ID = s.SKIER_ID
WHERE k.WEDSTRIJDTYPE = 'Dutch Cup snowboard '
AND k.SEIZOEN = '2016-2017'
order
by ATLEET_ID
, PUNTEN_WC DESC
) x
) y
where count < 6
) z
GROUP
BY ATLEET_ID
ORDER
BY GROEP_NAAM
, WC_RESULT DESC
LIMIT 0,2000;
问题是这个查询没有得到每个玩家的五个最佳分数。
当我运行最内部的查询时,它会对分数进行排序。
SELECT ATLEET_ID
, PUNTEN_WC
, k.SEIZOEN
, k.WEDSTRIJDTYPE
, g.GROEP_NAAM
, g.GROEP_OMS
FROM RESULTATEN r
LEFT
JOIN KALENDER k
ON r.KALENDER_ID = k.KALENDER_ID
JOIN GROEP_SNB g
ON r.GROEP_NAAM = g.GROEP_NAAM
JOIN SKIER s
ON r.ATLEET_ID = s.SKIER_ID
WHERE k.WEDSTRIJDTYPE = 'Dutch Cup snowboard '
AND k.SEIZOEN = '2016-2017'
order
by ATLEET_ID
, PUNTEN_WC DESC
我已经把记录数过了,所以我可以把它限制在最好的5个。但问题开始了。对于第二个查询,高分仍然正确排序,但计数字段不是0到5?
所以当我把第三个查询放进去时,计数字段是5,但是我希望每个玩家最多有5个分数。
最佳答案
您可以使用此查询对每个人的前N个值求和:
创建一个简单的测试表并填充它-
CREATE TABLE Scores
(`id` int, `playerName` varchar(16), `score` int)
;
INSERT INTO Scores
(`id`, `playerName`, `score`)
VALUES
(1, 'Joe', 5),
(2, 'Joe', 5),
(3, 'Joe', 5),
(4, 'Joe', 1),
(5, 'Joe', 10),
(6, 'Joe', 10),
(7, 'Joe', 15),
(8, 'Bob', 5),
(9, 'Bob', 5),
(10, 'Bob', 2),
(11, 'Bob', 10),
(12, 'Bob', 3),
(13, 'Bob', 10),
(14, 'Bob', 20)
;
查询:
SET @score_rank := 0;
SET @current_player = '';
SET @topN = 5;
Select playerName, SUM(score)
From (Select playerName, score,
@score_rank := IF(@current_player = playerName, (@score_rank + 1), 1) AS score_rank,
@current_player := playerName
From Scores
Order By playerName, score DESC) sorted
Where score_rank <= @topN
Group By playerName;
内部查询将值分配给两个变量-
@current_player
和@score_rank
。如果@current_player
值与playerName
匹配,则会增加@score_rank
,否则会将@score_rank
设置为1。通过这样做,我们只能抓住每个球员的前5名。然后外部查询将前5个分数相加。如果要对不同的集合求和(如前10个),可以更改@topN
的值。上述样本表的结果:
playerName SUM(score)
---------- ----------
Bob 50
Joe 45
请看这里:http://rextester.com/CLO11640