MySQL实现分组求和后查询总分最高(含同分)用户
问题背景
现有测试表Table1,建表语句及测试数据如下:
CREATE TABLE Table1 (`userid` varchar(11), `score` int, `type` varchar(22)); INSERT INTO Table1 (`userid`, `score`,`type`) VALUES (11, 2,'leader'), (11, 6,'leader'), (13, 6,'leader'), (15, 4,'leader'), (15, 4,'leader'), (12, 1,'leader'), (14, 1,'leader');
需求说明
- 筛选
type字段值为leader的记录 - 按
userid分组统计每个用户的score总和 - 返回总分最高的所有用户ID,存在多个用户总分并列最高时,需同时返回所有符合条件的用户
现有尝试的问题
已编写的查询语句如下:
SELECT userid, sum(score) as totalScore FROM Table1 WHERE type = "leader" GROUP BY userid ORDER BY totalScore DESC;
该语句会返回所有分组后的用户总分排序结果,无法仅筛选出总分最高的用户(当前测试数据下符合要求的是总分8的两个用户)。如果直接在语句末尾加LIMIT 1,会漏掉并列最高的用户,不符合需求。
可行SQL实现方案
方案1:通用子查询写法(兼容所有主流SQL版本)
该写法不依赖新版本特性,适配MySQL 5.x、老版本Oracle、SQL Server等所有支持标准SQL的数据库:
SELECT userid, totalScore FROM ( -- 先统计每个用户的总分 SELECT userid, SUM(score) AS totalScore FROM Table1 WHERE type = 'leader' GROUP BY userid ) user_total WHERE totalScore = ( -- 找到所有用户总分里的最大值 SELECT MAX(totalScore) FROM ( SELECT SUM(score) AS totalScore FROM Table1 WHERE type = 'leader' GROUP BY userid ) max_total );
逻辑说明:先完成分组统计得到每个用户的总分,再计算出总分的最高值,最后匹配所有总分等于最高值的用户,天然支持并列最高的场景。在当前测试数据下,该语句会返回userid=11(总分8)、userid=15(总分8)两条正确结果。
方案2:窗口函数写法(适配MySQL8.0+、PostgreSQL、Oracle12c+等新版本数据库)
如果你的数据库支持窗口函数,用RANK()写法更简洁,查询性能也更高:
SELECT userid, totalScore FROM ( SELECT userid, SUM(score) AS totalScore, -- 按总分降序排名,相同总分获得相同排名 RANK() OVER (ORDER BY SUM(score) DESC) AS score_rank FROM Table1 WHERE type = 'leader' GROUP BY userid ) ranked_total WHERE score_rank = 1;
注意事项:不要用ROW_NUMBER()替代RANK(),ROW_NUMBER()遇到相同总分时会给不同的排名值,会导致并列最高的用户被漏掉。
内容的提问来源于stack exchange,提问作者bijus
相关产品推荐
相关产品推荐

