【问题标题】:SQL Ranking with multiple rows [Same users will still have same rank ]多行 SQL Ranking [相同的用户仍将具有相同的排名]
【发布时间】:2015-11-14 22:51:25
【问题描述】:

我知道一点 SQL,我一直想知道如何从我的 Users 表中选择用户,我发现了这个:

SELECT *, FIND_IN_SET( Score, (    
    SELECT GROUP_CONCAT( Score ORDER BY Score DESC ) 
        FROM Users
    )
) AS Rank
FROM Users
WHERE UserID = 100
ORDER BY Score DESC

问题是,如果同一用户有多行,那么他们将分别获得排名。我想知道如何获得最高的Score 并让Rank 返回该值

它的样子(没有WHERE UserID = 100 子句):

ID-----UserID-----Score----Rank
1------100--------6--------1
2------192--------4--------2
3------192--------3--------3

我想要什么(没有WHERE UserID = 100 子句):

ID-----UserID-----Score----Rank
1------100--------6--------1
2------192--------4--------2
3------192--------3--------2

感谢您的帮助!

【问题讨论】:

  • 你到底想做什么?
  • @Blag 我想知道如何获得他们的最佳(最高)分数并让该排名成为被选中的排名(我可能应该更清楚)
  • 也许可以尝试使用GROUP BY(UserID)MAX(Score) 来获得maxScore
  • 创建小提琴显示预期结果
  • 好的,检查我的回答我认为它有效...

标签: mysql rank


【解决方案1】:

尝试以下方法:

SET @rank=0;
SELECT *, @rank:=@rank+1 AS rank
FROM Users
WHERE UserID = 100
ORDER BY Score DESC

【讨论】:

  • 问题是它的排名为空,它只会对选定的进行排名,而我目前使用的排名是每个人,但会遇到个人排名问题。
【解决方案2】:

使用GROUP BY(UserID)MAX(Score) 得到maxScore,然后对其进行排名。

(作为 OP 想要每一行用户,但只希望最好的排名,我们添加 INNER JOIN

SELECT TM.`UserID`, TM.`Score`, T3.`rank`
FROM `Users` as TM
INNER JOIN (
        SELECT `UserID`, FIND_IN_SET(
                Max(`Score`), (
                    select GROUP_CONCAT(
                        DISTINCT `Score`
                        order by `Score` DESC
                    )
                    From (
                        select MAX(`Score`) as `Score`
                        FROM `Users` as T0
                        GROUP BY `UserID`
                    ) as T1
                )
            ) as `rank`
        FROM `Users` as T2
        group by `UserID`
    ) as T3
    ON TM.`UserID` = T3.`UserID`
-- If we need to filter or sort, we make it here :
WHERE TM.`UserID` = 192
ORDER BY TM.`Score`

【讨论】:

  • 这是迄今为止最接近的一个,但它只向用户显示一次(不是他DISTICT 子句)我试图弄清楚如何,但我不能。(我不擅长这个高级 SQL)
  • 为什么要不止一次?因为它不是“正常的”,要么你保持最好的分数和排名,要么你得到每个分数的排名......;顺便说一句,这是第一个 MAX 和最后一个 GROUP BY 这样做的人
  • 我想要其他的,因为行内有更多信息。为了简单起见,我没有包括它。
  • 啊,我需要TM.UserID(它说UserID 含糊不清)谢谢大家的帮助:)
  • First part of query 然后是大部分任意数据。 Then the last part
【解决方案3】:

您可以计算每个得分较低的用户:

SELECT u.ID, u.UserID u.Score, 1 + COUNT(*) as Rank -- 1 + count every user with less score
FROM Users u
JOIN Users loser
  ON loser.Score < u.score -- join with every user having less score
GROUP BY u.ID, u.UserID, u.Score
ORDER BY Rank

【讨论】:

  • 你不能这样按分数分组...需要一个 MAX 才能获得最好的分数
  • 你是对的。在最好的情况下,我会得到与 OP 相同的结果(如果我修复了其他错误:-))
  • yes ;) (如果你看看我的最终版本,得到 OP 想要的 u_u 真是个大宝贝)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2022-01-27
  • 2021-07-08
  • 1970-01-01
相关资源
最近更新 更多