集計作業は、日々の業務でよく行われる作業の一つです。
例えば、月ごとの売上合計を計算したり、カテゴリごとに売れた商品の件数を数えたりします。
Excelで売上を管理している人なら、ピボットテーブルを使って自動的に集計することもありますね。
データベースでは、このような集計作業を「グルーピング」または、「 集約」と呼び、 GROUP BY句を使って実行します。
GROUP BY句は、
SELECT文でデータを特定の列ごとにグループ化するために使用されます。グループごとに集計関数(
SUM、
AVG、
COUNTなど)を適用することで、統計的な集計を行うことができます。
以下の
sales_dataテーブルを例に考えてみましょう。
| id | category | sales |
|---|---|---|
| 1 | 食品 | 1500 |
| 2 | 家電 | 3000 |
| 3 | 食品 | 2000 |
| 4 | 家具 | 5000 |
| 5 | 家電 | 2500 |
| 6 | 家具 | 3000 |
SELECT category, SUM(sales) AS total_sales
FROM sales_data
GROUP BY category;
このクエリは
sales_dataテーブルの
categoryごとに
salesの合計 (
SUM) を計算します。
このクエリを実行すると、以下のような集計結果が得られます。
| category | total_sales |
|---|---|
| 食品 | 3500 |
| 家電 | 5500 |
| 家具 | 8000 |
GROUP BY句では、さまざまな集約関数を利用してデータを集計できます。以下に代表的な関数を紹介します。
SUM()関数は、特定の列の合計を計算する際に使用します。
SELECT category, SUM(sales) AS total_sales
FROM sales_data
GROUP BY category;
AVG()関数は、特定の列の平均値を求めるために使用します。
SELECT category, AVG(sales) AS average_sales
FROM sales_data
GROUP BY category;
MAX()関数は、特定の列の最大値を取得する際に使用します。実際の現場でもよく使われる集計関数です。
SELECT category, MAX(sales) AS max_sales
FROM sales_data
GROUP BY category;
MIN()関数は、特定の列の最小値を取得する際に使用します。
SELECT category, MIN(sales) AS min_sales
FROM sales_data
GROUP BY category;
COUNT()関数は、特定のグループ内のデータ件数を取得する際に使用します。データの件数を数えることは、システムの基本ですので当然ながら頻繁に使われます。
SELECT category, COUNT(*) AS total_items
FROM sales_data
GROUP BY category;
GROUP BY句でもフィルタリング(絞り込み)が可能です。ただ、2種類あるので注意しましょう。
GROUP BY句とともに条件を指定する場合、
WHERE句と
HAVING句の違いを理解することが重要です。
WHERE句は
GROUP BYの前に適用され、グループ化される前のデータに対してフィルタリングを行います。
SELECT category, SUM(sales) AS total_sales
FROM sales_data
WHERE sales > 1000
GROUP BY category;
→
salesが 1000 を超えるデータのみを
GROUP BYの対象とします。
HAVING句は
GROUP BYの後に適用され、集約後のデータに対してフィルタリングを行います。
SELECT category, SUM(sales) AS total_sales
FROM sales_data
GROUP BY category
HAVING SUM(sales) > 5000;
→
categoryごとの
SUM(sales)が 5000 を超えるグループのみを取得します。
| WHERE | HAVING | |
|---|---|---|
| 適用タイミング | グループ化前 | グループ化後 |
| 使える条件 | 単純な列の条件 | 集約関数を含む条件 |
| 例 |
WHERE sales > 1000
|
HAVING SUM(sales) > 5000
|
業務では、月ごとの売上を集計するケースがよくあります。こちらのやり方も覚えておきましょう。
sales_data)
| id | sale_date | sales |
|---|---|---|
| 1 | 2024-01-05 | 1500 |
| 2 | 2024-01-15 | 3000 |
| 3 | 2024-02-10 | 2000 |
| 4 | 2024-02-20 | 5000 |
| 5 | 2024-03-05 | 2500 |
| 6 | 2024-03-25 | 3000 |
SELECT DATE_FORMAT(sale_date, '%Y-%m') AS sale_month, SUM(sales) AS total_sales
FROM sales_data
GROUP BY sale_month;
| sale_month | total_sales |
|---|---|
| 2024-01 | 4500 |
| 2024-02 | 7000 |
| 2024-03 | 5500 |
応用で年別の集計、週別の集計も可能です。
データをより詳細に分析するために、
GROUP BY句で複数のフィールドを指定してグルーピングすることが可能です。
SELECT category, DATE_FORMAT(sale_date, '%Y-%m') AS sale_month, SUM(sales) AS total_sales
FROM sales_data
GROUP BY category, sale_month;
このクエリを実行すると、
categoryと
sale_monthの組み合わせごとに
SUM(sales)を集計します。
| category | sale_month | total_sales |
|---|---|---|
| 食品 | 2024-01 | 1500 |
| 家電 | 2024-01 | 3000 |
| 食品 | 2024-02 | 2000 |
| 家具 | 2024-02 | 5000 |
| 家電 | 2024-03 | 2500 |
| 家具 | 2024-03 | 3000 |
このように、
GROUP BYで複数のカラムを指定することで、より詳細なデータ分析が可能になります。
GROUP BY句はデータをグループ化して集計する際に使用する。
WHEREはグループ化前のデータをフィルタリングし、
HAVINGはグループ化後のデータをフィルタリングする。
GROUP BYの
SELECTで取得できるのは、グループ化した列と集約関数を適用した列のみ。
この知識を活用し、効率的なクエリを作成できるようになりましょう!