关于HAVING子句行为的神话

时间:2012-02-28 11:45:10

标签: sql-server-2005 tsql group-by

我正在使用SQL Server 2005,我发现了HAVING子句的奇怪行为。

根据定义,HAVING子句假设用于处理数据 后的数据。但是,在COUNT子句中使用HAVING函数实际上在数据被分组之前应用于数据。

我在这里缺少什么?

示例数据:

DECLARE @ProductTypeIDsTable TABLE
(
    A INT
)

INSERT INTO @ProductTypeIDsTable(A) VALUES
(10),(12),(12),(9),(9),(9)

DECLARE @IDsTable TABLE
(
    B INT
)

INSERT INTO @IDsTable(B) VALUES
(9),(10),(12)

有问题的查询:

SELECT A 
    FROM @ProductTypeIDsTable pt 
    INNER JOIN @IDsTable ids ON pt.A = ids.B
    GROUP BY A
    --HAVING COUNT (A) = 1 -- gives 10 (repeated once due to the join)
    --HAVING COUNT (A) = 2 -- gives 12 (repeated twice due to the join)
    HAVING COUNT (A) = 3 -- gives 9 (repeated thrice due to the join)

1 个答案:

答案 0 :(得分:5)

如果在字段列表或having子句中使用聚合函数count,则不会给出不同的结果。

A上的常规小组:

select pt.A, count(*) as C
from @ProductTypeIDsTable pt
  inner join @IDsTable as ids
    on pt.A = ids.B
group by pt.A

结果:

A           C
----------- -----------
9           3
10          1
12          2

如果您在count子句中使用having,则此值就是您要比较的值。

如果您对group by之后返回的行数感兴趣,可以将查询放入如下的子查询中:

select count(*) as C
from
  (
    select pt.A
    from @ProductTypeIDsTable pt
      inner join @IDsTable as ids
        on pt.A = ids.B
    group by pt.A
  ) as T

结果:

C
-----------
3

<强>更新

来自HAVING (Transact-SQL)

  

指定组或聚合的搜索条件。

来自COUNT (Transact-SQL)

  

返回组中的项目数。