SELECT 中的多个聚合函数在 WHERE 中具有不同的条件

时间:2021-08-01 15:45:54

标签: mysql sql

给定这两个表:

Goals(Id,Player,isAuto)
Players(Id,Name,Team)

我想知道每个团队的总进球数和自动进球数。

到目前为止我的查询:

SELECT p.Team,COUNT(g.Id) AS Total,COUNT(g.isAuto) AS Auto
FROM Players p
JOIN Goals g
  ON p.Id=g.Player
WHERE g.isAuto=True
GROUP BY p.Team

这个查询的问题是 isAuto 的条件影响第一个 COUNT 函数的结果,我不知道如何使它成为 isAuto 上的条件只影响相应的 COUNT

2 个答案:

答案 0 :(得分:2)

SELECT p.Team
     , COUNT(g.Id) AS Total
     , COUNT(CASE WHEN g.isAuto = True THEN 1 END) AS Auto
  FROM Players p
  JOIN Goals g
    ON p.Id=g.Player
 GROUP BY p.Team
;

注意:对于我们希望显示没有目标的球员/球队的情况,请使用外连接。否则,内连接没问题。

答案 1 :(得分:1)

<块引用>

这个查询的问题是 isAuto 的条件影响了第一个 COUNT 函数的结果,我不知道怎么做,所以 isAuto 上的条件只影响相应的 COUNT。

聚合函数的结果是在 FROM 子句指定的源中满足通过 WHERE 子句指定的任何条件的行上计算的。您可以将其视为在将行聚合到计算聚合函数的组之前由 WHERE 条件过滤的行。您不能让 WHERE 子句仅应用于所选聚合函数的适当子集。

但是还有其他方法可以计算您想要获得的结果。特别是,如果 goals.isauto 是一个整数字段,仅限于包含值 01,那么您可以确定 SUM(g.isauto) 而不是 COUNT(g.isauto)

SELECT p.Team,COUNT(g.id) AS Total, SUM(g.isAuto) AS Auto
FROM Players p
JOIN Goals g
  ON p.Id=g.Player
WHERE g.isAuto=True
GROUP BY p.Team

如果 isauto 的域是别的东西,那么您可以计算 CASE 或其他执行适当转换的表达式的总和。例如,SUM(CASE WHEN g.isAuto > 0 THEN 1 ELSE 0 END)

还要注意 COUNT(g.id) 计算组中具有非空 g.id 的行数,但如果 g.id 是一个不可为空的主键,那么它总是全部行,更清楚地表示为 COUNT(*)