MySQL按歌手与歌曲分组获取最低Pos值的高效查询方案
高效获取每组最低排名的歌曲记录
针对songs表(含Artist、Title、Pos、Date字段)按Artist+Title分组,获取每组Pos值最低的完整记录需求,以下是几种高效单查询实现方案:
方案一:关联子查询
SELECT s.* FROM songs s WHERE s.Pos = ( SELECT MIN(Pos) FROM songs WHERE Artist = s.Artist AND Title = s.Title );
- 逻辑:先通过子查询定位每组的最小
Pos值,再匹配原表中对应条件的完整记录 - 优化建议:给
(Artist, Title)或(Artist, Title, Pos)创建联合索引,避免全表扫描,大幅提升查询速度
方案二:窗口函数(MySQL 8.0+适用)
SELECT Artist, Title, Pos, Date FROM ( SELECT *, ROW_NUMBER() OVER(PARTITION BY Artist, Title ORDER BY Pos ASC) AS rn FROM songs ) t WHERE rn = 1;
- 逻辑:用
ROW_NUMBER()按Artist+Title分组,组内按Pos升序标记行号,取行号为1的记录即为每组Pos最小的条目 - 扩展说明:若同一组存在多条
Pos相同的最小记录,需保留全部的话,可将ROW_NUMBER()替换为RANK()或DENSE_RANK()
方案三:分组JOIN
SELECT s.* FROM songs s JOIN ( SELECT Artist, Title, MIN(Pos) AS min_pos FROM songs GROUP BY Artist, Title ) t ON s.Artist = t.Artist AND s.Title = t.Title AND s.Pos = t.min_pos;
- 逻辑:先分组统计每组的最小
Pos,再通过JOIN关联原表获取对应完整记录 - 优化建议:同样需要给
(Artist, Title)添加联合索引,提升分组和关联效率
内容的提问来源于stack exchange,提问作者Nickmall
相关产品推荐
相关产品推荐

