使用Inner Join按指定年份范围SUM AB字段时求和异常的技术问询
问题:仅统计球员生涯特定年份范围的AB字段总和失败
我有两张表:
- Batting表:记录球员各年份数据,包含
Year字段(smallint类型) - Person表:包含球员的
DebutYear(出道年份)和FinalYear(退役年份)字段(均为smallint类型)
我想统计Batting表中处于DebutYear+1至DebutYear+2范围内的年份的AB字段总和,但当前写的SQL却把Batting表中所有年份的AB都求和了,求帮忙修正。
原错误SQL
SELECT CONCAT(FirstName, ' ', LastName) AS Name, B.PersonID, SUM(AB) AS AB FROM Batting B INNER JOIN Person P ON P.PersonID = B.PersonID AND (B.Year >= (P.DebutYear+1) AND B.Year <= (P.DebutYear+2)) WHERE B.PersonID = P.PersonID GROUP BY B.PersonID HAVING (AB >= 10000) ORDER BY AB Desc, LastName, FirstName LIMIT 1000
示例数据
Person表
| PersonID | Name | DebutYear |
|---|---|---|
| rosepe01 | Pete Rose | 1963 |
Batting表
| Batting | PersonID | Year | AB |
|---|---|---|---|
| 1 | rosepe01 | 1963 | 623 |
| 2 | rosepe01 | 1964 | 516 |
| 3 | rosepe01 | 1965 | 670 |
| 4 | rosepe01 | 1966 | 654 |
| 5 | rosepe01 | 1967 | 585 |
| 6 | rosepe01 | 1968 | 626 |
修正后的SQL
SELECT CONCAT(FirstName, ' ', LastName) AS Name, B.PersonID, SUM(AB) AS TotalAB FROM Batting B INNER JOIN Person P ON P.PersonID = B.PersonID AND B.Year BETWEEN (P.DebutYear + 1) AND (P.DebutYear + 2) GROUP BY B.PersonID, FirstName, LastName HAVING SUM(AB) >= 10000 ORDER BY TotalAB DESC, LastName, FirstName LIMIT 1000
修正说明
- 移除多余条件:删掉
WHERE B.PersonID = P.PersonID,INNER JOIN的ON条件已经完成两张表的关联,重复写无意义。 - 规范GROUP BY:将
FirstName和LastName加入GROUP BY,符合SQL标准,避免因模式设置导致的报错或结果异常。 - 优化条件写法:用
BETWEEN替代范围判断,逻辑不变但更简洁。 - 避免别名混淆:将聚合结果的别名改为
TotalAB,和原表的AB字段区分开;同时HAVING直接使用SUM(AB),避免部分SQL方言不支持在HAVING中使用聚合别名的问题。 - 关于求和范围错误的原因:你误以为所有年份被求和,大概率是因为原HAVING条件
AB >= 10000过滤掉了符合目标年份的小数据(比如示例中Pete Rose的目标年份总和仅1186,远低于10000),而如果存在球员所有年份AB总和刚好达标,就会让你产生误解。修正后的SQL会严格只统计DebutYear+1到DebutYear+2的AB总和。
内容的提问来源于stack exchange,提问作者studebaker
相关产品推荐
相关产品推荐

