SQLを学習していると、「GROUP BYした後なのに、なぜさらにPARTITION BYを使うの?」と疑問に感じる場面があります。特にウィンドウ関数を学び始めた頃は、「どちらもグループ化しているように見える」「同じことをしているのでは?」と混乱しやすいポイントです。この記事では、GROUP BYとPARTITION BYの役割の違いや、なぜ両方が必要になるのかを、実際のSQL例を使いながらわかりやすく整理します。
まずGROUP BYは「行をまとめて減らす」処理
GROUP BYは、同じ値を持つ行を1つにまとめるための構文です。
例えば、以下のような売上テーブルがあるとします。
| 社員 | 部署 | 売上 |
|---|---|---|
| A | 営業 | 100 |
| B | 営業 | 200 |
| C | 開発 | 150 |
ここで部署ごとの売上合計を求める場合はGROUP BYを使います。
SELECT 部署, SUM(売上)
FROM sales
GROUP BY 部署;
結果は次のようになります。
| 部署 | 合計売上 |
|---|---|
| 営業 | 300 |
| 開発 | 150 |
つまりGROUP BYは、複数行を1行に圧縮する処理です。
PARTITION BYは「行を消さずにグループ分けする」
一方、PARTITION BYはウィンドウ関数で使われる構文です。
こちらはGROUP BYとは違い、元の行を残したままグループ単位の計算を行います。
SELECT
社員,
部署,
売上,
SUM(売上) OVER(PARTITION BY 部署) AS 部署合計
FROM sales;
結果イメージは以下です。
| 社員 | 部署 | 売上 | 部署合計 |
|---|---|---|---|
| A | 営業 | 100 | 300 |
| B | 営業 | 200 | 300 |
| C | 開発 | 150 | 150 |
このように、元データを消さずに「部署ごとの集計結果」を各行へ付与できます。
なぜGROUP BYの後にPARTITION BYが必要になるのか
ここが最も混乱しやすいポイントです。
実は、GROUP BYとPARTITION BYは「役割」が違います。
| 構文 | 役割 |
|---|---|
| GROUP BY | 行をまとめて減らす |
| PARTITION BY | 行を残したまま計算範囲を分ける |
つまり、GROUP BYを実行した後でも、「その結果に対して順位付けしたい」「累積計算したい」「割合を出したい」という場合、PARTITION BYが必要になります。
よくある実務例
例えば「部署ごとの売上合計」を出した後、その中で順位を付けたいケースがあります。
SELECT
部署,
SUM(売上) AS 合計,
RANK() OVER(ORDER BY SUM(売上) DESC) AS 順位
FROM sales
GROUP BY 部署;
ここでは、まずGROUP BYで部署単位へ圧縮し、その結果に対してウィンドウ関数が動いています。
さらにPARTITION BYを組み合わせると、「年度ごとの部署順位」のような処理もできます。
AIが言う「前の処理を忘れる」はどういう意味か
AIが「前の処理を忘れる」と説明することがありますが、これは少し誤解を招きやすい表現です。
正確には、SQLは処理段階ごとに扱うデータ形状が変わるためです。
GROUP BYを実行すると、元の細かい行情報は集約されます。
そのため、その後の処理では「集約後の結果セット」に対して計算が行われます。
つまり、「忘れた」というより、すでに別の形の表へ変換されたイメージです。
イメージとしては「表を作り直している」
SQL初心者は、SQLを1行ずつ順番に読んでしまいがちですが、実際には段階的に新しい表を作っている感覚に近いです。
- FROMで元データ取得
- WHEREで絞り込み
- GROUP BYで集約表作成
- PARTITION BYで集約結果へ追加計算
この流れを理解すると、「なぜまたPARTITION BYするの?」がかなり理解しやすくなります。
GROUP BYだけではできないこと
GROUP BYは便利ですが、次のような処理は苦手です。
- 各行を残したまま集計
- 順位付け
- 累積合計
- 前行との差分
- 移動平均
こうした処理を行うために、PARTITION BYを使うウィンドウ関数が存在します。
初心者が混乱しやすいポイント
特に混乱しやすいのが、「どちらもグループ化しているように見える」点です。
しかし実際には、GROUP BYは「集約」、PARTITION BYは「計算範囲指定」です。
ここを区別すると、SQLがかなり理解しやすくなります。
まとめ
GROUP BYとPARTITION BYは似ているようで、役割が大きく異なります。
GROUP BYは行をまとめて減らす処理、PARTITION BYは行を残したまま計算単位を分ける処理です。
そのため、GROUP BYした後でも、順位付けや累積計算などを行う場合にはPARTITION BYが必要になります。
SQLでは「今どんな形の表を扱っているか」を意識すると、ウィンドウ関数の理解がかなり深まります。


コメント