4

我知道这是一个热门话题,但我仍然没有找到我想要的东西。我想查询一张表

BOOKS_READ
id
user_id
book_id

格式化列出已阅读书籍最多的用户的排行榜。当用户阅读一本书时,与 book id 和 user id 匹配的记录会登录到 books_read 表中。

是否可以对这个查询的结果进行排名,从 1 开始,并考虑平局?

SELECT user_id, COUNT(*) AS book_count 
FROM books_read 
GROUP BY user_id 
ORDER BY book_count DESC LIMIT 10

如果出现平局,我想在结果中列出一个“=”号。

例如,

rank  user_id  book_count  
=1    30       121
=1    17       121
 2    101      119
=3    11       104
=3    91       104

非常感谢您的帮助!我不介意使用 PHP 来处理其中的一些问题,但我对学习针对此类事情的直接 SQL 解决方案非常感兴趣 :-)

4

2 回答 2

2
SELECT GROUP_CONCAT(user_id, book_count
FROM (
    SELECT user_id, COUNT(*) AS book_count 
    FROM books_read 
    GROUP BY user_id 
    ORDER BY book_count DESC
) AS T1
GROUP BY book_count
ORDER BY book_count

给你

user_id  book_count  
30,17       121
101         119
11,91       104

然后您可以使用 PHP 来解析关系。

<?php
$rank = 1;

while ($row = mysql_fetch_assoc($result)) {
    $users = explode(',', $row['user_id'];
    foreach ($users as $user) {
        echo 'Rank: ' . $rank . ' ' . $user . "\n;
    }
    $rank++;
}

?>
于 2011-08-16T00:32:22.173 回答
1

你要做的就是统计得分比你感兴趣的记录更好的人数,然后加 1。

所以,如果你是最好的玩家,零人的得分更高,所以 0 + 1 = #1 排名。

如果五个人的分数更高,不管他们中有多少人并列,你仍然是 5 + 1 = 6。

问题在于,对于您显示的每一行,这是一种昂贵的查询。因此,您可能希望对结果集中的第一行执行此操作,然后在表示层 (PHP) 中为每个人添加一个。当你这样做时,一定要考虑到关系。

边缘条件是您不知道结果集中的第一行是否与“他”之前的人并列。因此,您需要知道有多少人与您的结果集中的第一个人得分相同。(如果您从顶部开始,这不是问题。)

于 2011-08-16T00:47:53.133 回答