集計と GROUP BY・HAVING

集計関数とGROUP BY/HAVINGの違いをコード例で押さえます。

集計関数とGROUP BY・HAVING。複雑そうに見えて、実は明確なルールがあります。

白峰 リリ(普段) 白峰 リリ

GROUP BY って、何のために使うの?

神楽 モニカ 先生(笑顔) 神楽 モニカ 先生

カテゴリごとに集計したいとき。 例えば『商品カテゴリごとの売上合計』を出すときに使うわ。

紅林 かえで(普段) 紅林 かえで

集計関数はSUM・AVG・COUNT・MIN・MAXが基本。 GROUP BY と組み合わせて、グループ内の値を1つに集約する。

-- カテゴリ別の売上合計と件数(売上1万円以上のグループのみ)
SELECT
  category,
  SUM(amount) AS total_sales,
  COUNT(*)    AS order_count,
  AVG(amount) AS avg_amount
FROM orders
WHERE ordered_at >= '2024-01-01'
GROUP BY category
HAVING SUM(amount) >= 10000
ORDER BY total_sales DESC;
藍沢 しずく(普段) 藍沢 しずく

WHERE と HAVINGの違いって何ですかぁ?

紅林 かえで(普段) 紅林 かえで

WHERE は集計前の行絞り込み、HAVING は集計後のグループ絞り込み。 上の例だと『2024年以降の注文だけを集計し、合計1万円以上のカテゴリだけ表示』。

白峰 リリ(笑い) 白峰 リリ

なるほど!
WHEREが先で、HAVINGが後ってことね!

神楽 モニカ 先生(普段) 神楽 モニカ 先生

実行順序: FROM → WHERE → GROUP BY → HAVING → SELECT → ORDER BY → LIMIT。 これを覚えておくと、エラー時に原因を特定しやすいわ。

紅林 かえで(普段) 紅林 かえで

GROUP BY を使ったとき、SELECT には『GROUP BY の列』か『集計関数の結果』しか使えない。 これが守られないとSQLエラー。

藍沢 しずく(普段) 藍沢 しずく

COUNT(*) と COUNT(列名) って、どう違うんですかぁ?

紅林 かえで(普段) 紅林 かえで

COUNT(*)は行数、COUNT(列名)はNULL以外の値の数。 NULL を除いた件数を数えたいときに使い分ける。

白峰 リリ(普段) 白峰 リリ

じゃあ、DISTINCT は?

神楽 モニカ 先生(普段) 神楽 モニカ 先生

COUNT(DISTINCT 列) で『重複を除いた値の数』。 例えば DISTINCT user_id でユニークユーザー数。 これも頻出よ。

確認クイズ

売上合計が10万円以上のカテゴリのみ表示したい。 適切な条件指定はどれか。

  1. WHERE SUM(amount) >= 100000
  2. GROUP BY SUM(amount) >= 100000
  3. HAVING SUM(amount) >= 100000
  4. ORDER BY SUM(amount) >= 100000
こたえを見る

正解: 3. HAVING SUM(amount) >= 100000

HAVING SUM(amount) >= 100000。 集計後の絞り込みは HAVING を使います。 WHEREには集計関数を書けないため、グループの合計値で絞り込む場合はHAVINGが必須です。

🔖 この記事の関連書籍

Amazonアソシエイトリンクを含みます。他分野は おすすめ書籍ページ へ。