首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 數據庫知識 >  >> MySQL 資料庫 >> MySQL 綜合教學

SQL 多欄位 GROUP BY 分組邏輯深度解析

     編輯:MySQL 綜合教學

SQL 多欄位 GROUP BY 分組邏輯深度解析

當 GROUP BY 指定兩個以上欄位時,資料庫會依「先後順序」進行遞迴分組。本文透過實測資料與圖解,詳細說明多鍵分組的運作機制與結果差異。

測試資料建立

CREATE TABLE test (
    a VARCHAR(20),
    b VARCHAR(20),
    c VARCHAR(20)
);

INSERT INTO test VALUES
('1','a','甲'), ('1','a','甲'), ('1','a','甲'), ('1','a','甲'),
('1','a','乙'),
('1','b','乙'), ('1','b','乙'), ('1','b','乙');

原始資料 (8 筆):

+---+---+---+
| a | b | c |
+---+---+---+
| 1 | a | 甲 |
| 1 | a | 甲 |
| 1 | a | 甲 |
| 1 | a | 甲 |
| 1 | a | 乙 |
| 1 | b | 乙 |
| 1 | b | 乙 |
| 1 | b | 乙 |
+---+---+---+

單欄位分組基準

  • GROUP BY b:a 群組 5 筆、b 群組 3 筆
  • GROUP BY c:甲 群組 4 筆、乙 群組 4 筆

雙欄位分組:GROUP BY b, c

SELECT COUNT(a), b, c FROM test GROUP BY b, c;

結果:

+-----------+---+---+
| COUNT(a)  | b | c |
+-----------+---+---+
| 4         | a | 甲 |
| 1         | a | 乙 |
| 3         | b | 乙 |
+-----------+---+---+

雙欄位分組:GROUP BY c, b (順序互換)

SELECT COUNT(a), b, c FROM test GROUP BY c, b;

結果:

+-----------+---+---+
| COUNT(a)  | b | c |
+-----------+---+---+
| 4         | a | 甲 |
| 1         | a | 乙 |
| 3         | b | 乙 |
+-----------+---+---+

核心邏輯:分組如「剝洋蔥」

GROUP BY b, c 執行過程:

  1. 第一層:依 b 切分 → 群組 1 (b='a',第 1-5 筆)、群組 2 (b='b',第 6-8 筆)
  2. 第二層:在各群組內再依 c 細分
    • 群組 1 依 c 分為:c='甲' (4 筆)、c='乙' (1 筆)
    • 群組 2 依 c 分為:c='乙' (3 筆)
  3. 最終形成 3 個最細粒度群組

結論:GROUP BY b, c 與 GROUP BY c, b 最終聚合結果相同 (相同鍵值組合、相同計數),但輸出順序可能不同 (視 DBMS 排序實作)。

實務應用場景

場景GROUP BY 組合說明
銷售報表region, product_category, month依區域→產品類→月份層層匯總
網站流量分析date, channel, device依日期→管道→裝置分組
庫存管理warehouse, sku, batch依倉庫→SKU→批次追蹤

常見錯誤與注意事項

  • SELECT 清單錯誤:未出現在 GROUP BY 的非聚合欄位會報錯 (ONLY_FULL_GROUP_BY 模式)。
  • NULL 值處理:NULL 會形成獨立群組,若需合併請用 COALESCE(col, 'UNKNOWN')。
  • 效能考量:多欄位分組需掃描更多資料,建議在組合鍵上建立複合索引 INDEX idx_b_c (b, c)。
  • HAVING 搭配:HAVING COUNT(*) > 1 可過濾低頻群組。

進階:GROUPING SETS / ROLLUP / CUBE (支援 DB: PostgreSQL, Oracle, SQL Server)

# 一次產生多層級彙總
SELECT b, c, COUNT(*) 
FROM test 
GROUP BY ROLLUP (b, c);
# 等同於: GROUP BY b, c + GROUP BY b + GROUP BY ()

掌握多欄位分組邏輯,能撰寫出精準、高效的多維度統計查詢。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved