如何让SQL查询仅返回每个PlayerID对应的第一条结果?
解决方法:按PlayerID分组获取第一条记录
首先,你用DISTINCT无效的原因是:每一行的Weapon字段值都不同,所以CharacterName, PlayerID, Class, Race, Alignment, Weapon的组合都是唯一的,DISTINCT无法实现你想要的去重效果。要实现每个PlayerID只返回第一条记录,需要用窗口函数或分组子查询的方式,具体取决于你使用的数据库。
通用方案(适用于支持窗口函数的数据库:MySQL 8.0+/PostgreSQL/SQL Server/SQLite 3.25+)
使用ROW_NUMBER()窗口函数,按PlayerID分组后给每组内的记录排序,再取每组的第一条:
SELECT CharacterName, PlayerID, Class, Race, Alignment, Weapon FROM ( SELECT CharacterName, PlayerID, Class, Race, Alignment, Weapon, ROW_NUMBER() OVER (PARTITION BY PlayerID ORDER BY Weapon) AS row_num FROM CharacterTable ) AS ranked WHERE row_num = 1;
关键说明:
PARTITION BY PlayerID:将数据按PlayerID分组ORDER BY Weapon:定义每组内的排序规则(你可以替换成主键、创建时间等字段,确保"第一条"是你预期的顺序)row_num = 1:筛选出每组的第一条记录
MySQL 5.x 兼容方案(不支持窗口函数)
如果你的MySQL版本低于8.0,可以用子查询关联的方式实现:
SELECT c1.* FROM CharacterTable c1 LEFT JOIN CharacterTable c2 ON c1.PlayerID = c2.PlayerID AND c1.Weapon > c2.Weapon WHERE c2.Weapon IS NULL;
说明:
这个查询会返回每个PlayerID中Weapon值最小的那条记录(如果需要最大的,把>换成<即可)。若要按其他字段排序,修改ON子句中的比较条件即可。
重要提示
- 必须指定
ORDER BY的字段,否则数据库返回的"第一条"是随机的(取决于存储引擎的物理存储顺序)。 - 只有当同一个
PlayerID的所有字段完全相同时,DISTINCT才会生效,但你的数据中Weapon字段各不相同,所以该方法不适用。
内容的提问来源于stack exchange,提问作者SkyeBoniwell
相关产品推荐
相关产品推荐

