MySQL基本操作整理(三)、分組函數與分組查詢

本文介紹MySQL基本操作中的分組函數與分組查詢操作,並用幾個案例來具體說明,加深對分組查詢的認知。

一、分組函數

1.功能

MySQL分組函數用作統計使用,又稱爲聚合函數或統計函數或組函數
具體一點理解:給定一組值(如一個數據表),通過分組函數來獲取某一個值

2.分類

sum 求和、avg 平均值、max 最大值 、min 最小值 、count 計算個數

3.特點總結

  1. sum、avg一般用於處理數值型(不能處理字符串類型與日期類型,處理日期類型無意義)
    max、min、count可以處理任何類型(字符串、日期等,count計算非空個數)
  2. 以上分組函數都忽略null值
  3. 可以和 distinct 搭配實現去重的運算
  4. count函數的介紹
    一般使用count(*)用作統計行數
  5. 和分組函數一同查詢的字段要求是group by後的字段

4.具體案例

  1. 分組函數參數支持的類型
//前兩條查詢語句沒有意義,SUM和AVG函數一般用於處理數值類型
SELECT SUM(last_name) ,AVG(last_name) FROM employees;
SELECT SUM(hiredate) ,AVG(hiredate) FROM employees;
//字符串也能排序,可以求最大、最小值;COUNT函數計算非空字段的行數
SELECT MAX(last_name),MIN(last_name) FROM employees;
SELECT MAX(hiredate),MIN(hiredate) FROM employees;
SELECT COUNT(commission_pct) FROM employees;
SELECT COUNT(last_name) FROM employees;
  1. 以上分組函數都忽略null值
//在下面的語句中,AVG(commission_pct)和SUM(commission_pct)/35的結果相同,因爲總共107條記錄,其中有72條記錄是沒有獎金的
SELECT SUM(commission_pct) ,AVG(commission_pct),SUM(commission_pct)/35,SUM(commission_pct)/107 FROM employees;
//最大最小函數也忽略null值
SELECT MAX(commission_pct) ,MIN(commission_pct) FROM employees;
//COUNT函數忽略null值
SELECT COUNT(commission_pct) FROM employees;
SELECT commission_pct FROM employees;
  1. 可以和 distinct 搭配實現去重的運算
SELECT SUM(DISTINCT salary),SUM(salary) FROM employees;

SELECT COUNT(DISTINCT salary),COUNT(salary) FROM employees;
  1. count函數詳細介紹
//COUNT函數統計非null的行數
SELECT COUNT(salary) FROM employees;
SELECT COUNT(*) FROM employees; #只要有一個屬性字段的值爲非null,則count+1
SELECT COUNT(1) FROM employees; #在每一行前面加了個1,然後統計1的個數,就是統計行數,作用和COUNT(*)相同
SELECT COUNT(2) FROM employees;以及SELECT COUNT("任意字符串") FROM employees;效果都和COUNT(*)類似

效率問題分析:
MYISAM存儲引擎下 ,COUNT( * )的效率高
INNODB存儲引擎下,COUNT( * )和COUNT(1)的效率差不多,比COUNT(字符串)要高一些(要先判斷該字符串的值是否爲null)

  1. 和分組函數一同查詢的字段有限制
//以下查詢結果沒有意義
SELECT AVG(salary),employee_id  FROM employees; #解釋一下AVG(salary)查出來是一個值,而employee_id查出來是很多值,最終顯示的是一行數據,employee_id無論顯示誰都沒意義
//正確的用法,和分組函數一同查詢的需要時GROUP BY後面的字段
SELECT AVG(salary),department_id FROM employees GROUP BY department_id;

二、分組查詢

1.語法

select 分組函數, 列(該列出現在group by 的後面)
from 表
【where 篩選條件】
group by 分組的字段
【having 分組後篩選條件】
【order by 排序的字段】;

2.特點

  • 和分組函數一同查詢的字段必須是group by後出現的字段
  • 分組查詢中的篩選條件分爲兩類:分組前篩選和分組後篩選
分類 針對的表 位置 連接的關鍵字
分組前篩選 原始表 group by前 where
分組後篩選 group by後的結果集 group by後 having

小結:
(1) 分組函數做篩選條件肯定是放在having子句中
(2) 一般來講,能用分組前篩選的,儘量使用分組前篩選,提高效率

  • 分組可以按單個字段也可以按多個字段分組(多個字段之間用逗號隔開,沒有順序要求),也可以按照表達式分組(用的較少)
  • 可以搭配着排序使用,放在整個分組查詢的最後

3.具體案例

  1. 簡單分組
#案例1:查詢每個工種的員工平均工資
SELECT AVG(salary),job_id
FROM employees
GROUP BY job_id;

#案例2:查詢每個位置的部門個數
SELECT COUNT(*),location_id
FROM departments
GROUP BY location_id;
  1. 添加分組前的篩選條件
#案例1:查詢郵箱中包含a字符的 每個部門的最高工資
SELECT MAX(salary),department_id
FROM employees
WHERE email LIKE '%a%'
GROUP BY department_id;

#案例2:查詢有獎金的每個領導手下員工的平均工資
SELECT AVG(salary),manager_id
FROM employees
WHERE commission_pct IS NOT NULL
GROUP BY manager_id;
  1. 添加分組後的篩選條件
#案例:查詢哪個部門的員工個數>5
# (1)查詢每個部門的員工個數
SELECT COUNT(*),department_id
FROM employees
GROUP BY department_id;
#(2)篩選剛纔(1)的結果
SELECT COUNT(*),department_id
FROM employees
GROUP BY department_id
HAVING COUNT(*)>5; (這裏不能把HAVING寫成WHERE COUNT(*) > 5放在GROUP BY前面)

#案例2:查詢每個工種有獎金的員工的最高工資>12000的工種編號和最高工資

SELECT job_id,MAX(salary)
FROM employees
WHERE commission_pct IS NOT NULL
GROUP BY job_id
HAVING MAX(salary)>12000;

#案例3:領導編號>102的每個領導手下的最低工資大於5000的領導編號和最低工資

SELECT manager_id,MIN(salary)
FROM employees
WHERE manager_id > 102
GROUP BY manager_id
HAVING MIN(salary)>5000;
  1. 表達式或函數分組
#案例:按員工姓名的長度分組,查詢每一組的員工個數,篩選員工個數>5的有哪些員工
SELECT COUNT(*),LENGTH(last_name) 
FROM employees 
GROUP BY LENGTH(last_name) 
HAVING COUNT(*) > 5;
  1. 多個字段分組
#案例:查詢每個工種每個部門的最低工資,並按最低工資降序
SELECT MIN(salary),job_id,department_id
FROM employees
GROUP BY department_id,job_id
ORDER BY MIN(salary) DESC;

注意代碼中分組字段的位置順序可以任意,達到的每一個分組是一樣的效果

  1. 添加排序
#案例:每個工種有獎金的員工的最高工資>6000的工種編號和最高工資,按最高工資升序(可以給最高工資起別名)

SELECT job_id,MAX(salary) m
FROM employees
WHERE commission_pct IS NOT NULL
GROUP BY job_id
HAVING m>6000
ORDER BY m ;
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章