行数を取得するCOUNT(*)で少しハマったのでメモ。

WHERE句で存在しない行を条件にしてCOUNT()すると、0件として取得できます。 その動きを想定してうっかりGROUP BYでグルーピングをしつつCOUNT()しちゃうと、対象のレコードが存在しないので0件として取得できない。当然ですね。でもハマってしまいました。

ということでサンプルです。

-- サンプルデータ
drop table if exists dbo.Sample;
create table dbo.Sample(
    GroupId int not null,
    Value nvarchar(5) not null
);

insert into dbo.Sample(GroupId, Value)
output inserted.*
values
    (1, N'a'),
    (1, N'b'),
    (2, N'c');
/*
GroupId     Value
----------- -----
1           a
1           b
2           c
*/

WHEREで存在しないグループを条件に指定し、グルーピングしないクエリでは、0件として取得できます。

declare @groupId int = 3;

-- グルーピングしなければOK
select count(*)
from dbo.Sample
where GroupId = @groupId
/*
Count
-----
0
*/

WHEREで存在しないグループを条件に指定しつつ、GROUP BYしてしまうと結果が空になります。

-- うっかりグルーピングしちゃうとダメ
select GroupId, count(*)
from dbo.Sample
where GroupId = @groupId
group by GroupId;
/*
GroupId     Count
----------- -----
*/