我正在查询SSMS中非常流行的AdventureWorks DB。 我的目标是从HumanResources.Employee中找到每个职位下的男性和女性人数。
为此,我最初的查询是
SELECT JobTitle,
COUNT(CASE WHEN Gender='M' THEN 1
ELSE 0
END) AS MALE_COUNT,
COUNT(CASE WHEN Gender='F' THEN 1
ELSE 0
END) AS FEMALE_COUNT,Gender
FROM HumanResources.Employee
GROUP BY JobTitle,Gender
ORDER BY JobTitle
GO
但是,我对上述查询的回答不正确。因此,通过如下修改,我得到了预期的结果:
SELECT JobTitle,
COUNT(CASE WHEN Gender='M' THEN 1
END) AS MALE_COUNT,
COUNT(CASE WHEN Gender='F' THEN 1
END) AS FEMALE_COUNT,Gender
FROM HumanResources.Employee
GROUP BY JobTitle,Gender
ORDER BY JobTitle
GO
很容易看出,我只是删除了两个CASE语句的“ ELSE 0”条件,但是我无法弄清楚“ 0”如何影响结果中返回的值。
有人可以向我解释这两者之间的区别吗?我也想知道COUNT函数如何取多个值,通常情况下(例如SELECT COUNT(3,3))不起作用。
答案 0 :(得分:2)
您想要SUM()
,而不是COUNT()
:后者考虑了每个非{null
值(其中包括0
),因此您当前的条件表达式计算所有行-相当于COUNT(*)
此外,我怀疑gender
和SELECT
子句中不应出现GROUP BY
,因为这正是您要汇总的内容
我认为您想要
SELECT
JobTitle,
SUM(CASE WHEN Gender='M' THEN 1 ELSE 0 END) AS MALE_COUNT,
SUM(CASE WHEN Gender='F' THEN 1 ELSE 0 END) AS FEMALE_COUNT
FROM HumanResources.Employee
GROUP BY JobTitle
ORDER BY JobTitle
答案 1 :(得分:1)
文档说:
COUNT(ALL表达式)计算组中每一行的表达式, 并返回非空值的数量。
在此处了解更多信息:https://docs.microsoft.com/en-us/sql/t-sql/functions/count-transact-sql?view=sql-server-ver15
因此我们可以将您的查询重写为:
SELECT
JobTitle,
COUNT(CASE WHEN Gender='M' THEN 1 ELSE NULL END) AS MALE_COUNT,
COUNT(CASE WHEN Gender='F' THEN 1 ELSE NULL END) AS FEMALE_COUNT
FROM HumanResources.Employee
GROUP BY JobTitle
ORDER BY JobTitle
关于您的查询:
第一个查询:
在Count函数内部,您有一个CASE
表达式,该表达式会将'M'更改为1,将'F'更改为0。然后COUNT
函数将对其进行计数操作。因为1和0都不为NULL,所以Count
将返回记录总数,而不考虑'M'或'F'
第二CASE
的步骤也相同。
第二个查询:
在Count
函数内部,您有一个CASE
表达式,该表达式会将'M'更改为1,但是您没有提到如何处理其他值,因此对于非M值,将返回NULL。 。之后,Count
函数将对这些记录进行计数操作并返回M的数量。(第二个查询等于我发布的查询,并且它们都具有相同的输出。但是由于可读性,我比您的查询更喜欢我的查询:-))
第二CASE
的步骤也相同。
CASE
表达式的文档说:
ELSE else_result_expression是否返回表达式? 比较运算的结果为TRUE。如果省略此参数 并且没有比较运算的结果为TRUE,CASE返回NULL。 else_result_expression是任何有效的表达式。的数据类型 else_result_expression和任何result_expression必须相同或 必须是隐式转换。
在此处了解更多信息:https://docs.microsoft.com/en-us/sql/t-sql/language-elements/case-transact-sql?view=sql-server-ver15
选择计数(3,3)
这在语法上是错误的,并且会给您这样的错误,这很容易解释:
消息174,级别15,状态1,第1行计数功能需要1 论点
基于上述文档的Count
函数的语法如下:
-- Aggregation Function Syntax
COUNT ( { [ [ ALL | DISTINCT ] expression ] | * } )
-- Analytic Function Syntax
COUNT ( [ ALL ] { expression | * } ) OVER ( [ <partition_by_clause> ] )