我想做一个排名,把最好的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

09-12 10:51