SQL技术求助:马匹赛事相关查询及语句报错排查
解决你的SQL查询问题
首先,我得先假设你的数据表结构(毕竟你没给出具体结构,这是最常见的赛马数据模型):
horses:存储马的基本信息,字段包括horse_id(主键,唯一标识每匹马)、horse_name(马的名称)races:存储赛事的冠军信息,字段包括race_id(主键,唯一标识每场赛事)、winner_horse_id(关联horses.horse_id,记录这场比赛的冠军马ID)- 如果要统计马参与但未获胜的赛事,还需要一个
race_participants表:记录每匹马参与的赛事,字段包括race_id、horse_id(关联horses.horse_id)
第一个查询:每匹马的名称 + 获胜/未获胜赛事数量
场景1:统计马参与过的赛事中的胜负次数
如果你的数据库有race_participants表(记录马的参赛情况),用这个SQL:
SELECT h.horse_name, -- 统计获胜的赛事数:只计数该马是冠军的赛事 COUNT(DISTINCT CASE WHEN r.winner_horse_id = hp.horse_id THEN hp.race_id END) AS win_count, -- 统计未获胜的赛事数:计数该马参赛但没拿冠军的赛事 COUNT(DISTINCT CASE WHEN r.winner_horse_id != hp.horse_id THEN hp.race_id END) AS loss_count FROM horses h -- 左连接确保所有马都被包含,哪怕没参加过任何比赛 LEFT JOIN race_participants hp ON h.horse_id = hp.horse_id LEFT JOIN races r ON hp.race_id = r.race_id GROUP BY h.horse_id, h.horse_name;
场景2:统计所有赛事中该马的夺冠/未夺冠次数(仅当你不需要区分参赛与否时用)
如果没有参赛表,只想算所有赛事里它没夺冠的数量(意义相对弱,但满足需求):
SELECT h.horse_name, COUNT(r.race_id) AS win_count, -- 总赛事数减去夺冠数就是未夺冠数 (SELECT COUNT(*) FROM races) - COUNT(r.race_id) AS loss_count FROM horses h LEFT JOIN races r ON h.horse_id = r.winner_horse_id GROUP BY h.horse_id, h.horse_name;
第二个查询:每匹马的夺冠次数(未夺冠显示0)+ 降序排序
这个需求的核心是不要过滤掉未夺冠的马,并且把NULL的夺冠数转成0,用LEFT JOIN和COALESCE就能解决:
SELECT h.horse_name, -- COALESCE把NULL(没夺冠的马)转成0 COALESCE(COUNT(r.race_id), 0) AS first_place_count FROM horses h -- 左连接保留所有马,哪怕没拿过冠军 LEFT JOIN races r ON h.horse_id = r.winner_horse_id -- 按马的唯一标识分组,避免重复统计 GROUP BY h.horse_id, h.horse_name -- 按夺冠次数降序排序 ORDER BY first_place_count DESC;
你可能遇到的报错原因
我猜你第一次执行报错大概率是这几个问题:
- 用了
INNER JOIN而非LEFT JOIN:INNER JOIN会过滤掉没夺冠/没参赛的马,不仅结果不对,还可能因为分组逻辑报错 - 没正确处理
GROUP BY:如果你的数据库开启了严格模式(比如MySQL的ONLY_FULL_GROUP_BY),必须把SELECT里的非聚合字段都放进GROUP BY里(比如horse_id和horse_name),不然会报错 - 没处理
NULL值:未夺冠的马用COUNT(r.race_id)会得到NULL,如果直接返回不符合需求,还可能在排序时出问题 - 关联字段写错:比如把
races.winner_horse_id写成races.horse_id,导致关联错误,统计完全不对
内容的提问来源于stack exchange,提问作者beginIT
相关产品推荐
相关产品推荐

