プログラミング

【備忘】SQLのCOUNT関数で集計する時の基礎(引数の意味と条件つける方法)

今回はCOUNT関数を使うとき個人的にこれだけは覚えておきたい2つの基礎をまとめておきます。

前提

環境:PostgreSQL17

で実施しています。

また、今回は前提として簡単なテーブルとデータを用意してます。

実際に同じ条件で試したい場合は、最初にテーブルとデータを作ってください。

自分の環境で試す場合は、不要です。

関数の引数で集計結果が変わる

COUT(*)としがちですが、引数にはしっかり意味があります。

引数によってSQLの結果が変わることを覚えておきましょう。

パラメータ説明
*NULLを含めたレコード数
1NULLを含めたレコード件数
カラム名NULLを含まないレコード数
DISTINCT カラム名NULLと重複を含まないレコード件数

実際にSQLを実行すると以下のようになります。

結果を見て分かるように「*」「1」とした場合、NULLのレコードも含んでしまうこと重要です。

用途によって、しっかりと理解して使い分けるようにしましょう。

SELECT COUNT(*) FROM test;

---------------------
count
7

SELECT COUNT(1) FROM test;

---------------------
count
7

SELECT COUNT(type) FROM test;

---------------------
count
6

SELECT COUNT(DISTINCT(type)) FROM test;

---------------------
count
2

条件をつけて集計する

COUNT関数では条件をつけて集計することもできます。

引数で条件をつけることができます。今回はCASEを使う方法と使わない方法を載せておきます。

①CASEを使わない

以下のように条件をつけることで、「typeが1のレコードの件数をカウント」することができます。

-- typeが1のレコードの件数をカウント
SELECT COUNT(type=1 OR NULL) FROM test;

---------------------
count
3

ここでのポイントはSQLでは3値論理が採用されていることです。

3値論理は下表を参考にしてください。

そのため、「typeが1のレコードの件数をカウント」するために条件に「OR NULL」を追加しています。

aba AND ba OR b
TRUETRUETRUETRUE
TRUEFALSEFALSETRUE
TRUENULLNULLTRUE
FALSEFALSEFALSEFALSE
FALSENULLFALSENULL
NULLNULLNULLNULL

ちなみに、「OR NULL」をつけない場合、このようになります。

-- typeが1のレコードの件数をカウント
SELECT COUNT(type=1) FROM test;

---------------------
count
6

②CASEを使う

引数にCASEを使うこともできます。

引数にCASEを使って条件に一致する場合はTrue、一致しない場合はNULLとすることで「typeが1のレコードの件数をカウント」することができます。

-- typeが1のレコードの件数をカウント
SELECT COUNT(CASE WHEN type=1 THEN TRUE ELSE NULL END) FROM test;

---------------------
count
3

この時、NULLではなく、Falseにしてもいいのではと思うかもしれませんが、Falseにすると正しい結果を取得できないので注意です。

-- typeが1のレコードの件数をカウント
SELECT COUNT(CASE WHEN type=1 THEN TRUE ELSE FALSE END) FROM test;

---------------------
count
7

-プログラミング
-