目录
⚪使用count(*),count(1),count(具体字段)哪个效率更好呢?
需求2:查询各个department_id,job_id的平均工资
一、聚合函数介绍
1.概念
聚合函数作用于一组数据,并对一组数据返回一个值。
2.聚合函数的类型
①AVG和SUM函数
只适用于数值类型的字段(或变量)
SELECT AVG(salary),SUM(salary),AVG(salary)*107
FROM employees;
#如下的操作是没有意义的
SELECT SUM(last_name),AVG(last_name),SUM(hire_date)
FROM employees;
②MIN和MAX函数
适用于数值类型、字符串类型、日期时间类型的字段(或变量)
SELECT MAX(salary),MIN(salary),MAX(hire_date),MIN(hire_date)
FROM employees;
③COUNT函数
计算指定字段在查询结构中出现的个数
SELECT COUNT(employee_id),COUNT(salary),COUNT(2*salary),COUNT(1)
FROM employees;
Ⅰ.如何实现计算表中有多少条记录?
方式1:COUNT(*)
方式2:COUNT(1)
方式3:COUNT(具体字段) —— 不一定是正确的
注意:计算指定字段出现的个数时,是不计算NULL值的
Ⅱ.AVG = SUM/COUNT
SELECT AVG(salary),SUM(salary)/COUNT(salary),
AVG(commission_pct),SUM(commission_pct)/COUNT(commission_pct),
SUM(commission_pct) / 107
FROM employees;
Ⅲ.查询公司中平均奖金率
#错误写法
SELECT AVG(commission_pct)
FROM employees;
#正确写法
SELECT SUM(commission_pct) / COUNT(IFNULL(commission_pct,0)),
AVG(IFNULL(commission_pct,0))
FROM employees;
⚪使用count(*),count(1),count(具体字段)哪个效率更好呢?
如果使用的是MYISAM存储引擎,则三者效率相同,都是O(1)
如果使用的是InnoDB存储引擎,则三者效率count(*) = count(1) > count(具体字段)
二、GROUP BY的使用
需求1:查询各个部门的平均工资,最高工资
SELECT AVG(salary)
FROM employees; #整个公司的平均工资
SELECT department_id,AVG(salary),MAX(salary)
FROM employees
GROUP BY department_id;
需求2:查询各个department_id,job_id的平均工资
SELECT department_id,job_id,AVG(salary)
FROM employees
GROUP BY department_id,job_id;
结论
1.SELECT 中出现的非组函数的字段,必须声明在GROUP BY中。反之,GROUP BY中声明的字段可以不出现在SELECT中
2.GROUP BY声明在FROM后面、WHERE后面,ORDER BY前面、LIMIT前面
3.在MySQL中使用 WITH ROLLUP:在所有查询出的分组记录之后增加一条记录,该记录计算查询出的所有记录的总和,即统计记录数量。
三、HAVING的使用
1.作用
过滤数据
2.练习:查询各个部门中最高工资比10000高的部门信息
#错误写法
SELECT department_id,MAX(salary)
FROM employees
WHERE MAX(salary) > 10000
GROUP BY department_id;
#正确写法
SELECT department_id,MAX(salary)
FROM employees
GROUP BY department_id
HAVING MAX(salary) > 10000;
要求
- 如果过滤条件中使用了聚合函数,则必须使用HAVING来替换WHERE,否则会报错
- HAVING必须声明在GROUP BY的后面
- 开发中,使用HAVING的前提是SQL中使用了GROUP BY
四、SQL底层的执行原理
当过滤条件中有聚合函数时,则此过滤条件必须声明在HAVING中
当过滤条件中没有聚合函数时,则此过滤条件声明在WHERE中或HAVING中都可以,但是,建议大家声明在WHERE中
(一)WHERE与HAVING的对比
1.适用范围
HAVING的适用范围更广
2.如果过滤条件没有聚合函数时
WHERE的执行效率高于HAVING
总结
(二)SELECT语句
1.SQL92的语法
SELECT ......(存在聚合函数)
FROM ......
WHERE 多表的连接条件 AND 不包含聚合函数的过滤条件
GROUP BY ......
HAVING 包含聚合函数的过滤条件
ORDER BY ......(ASC / DESC)
LIMIT ......
2.SQL99的语法
SELECT ......(存在聚合函数)
FROM .... (LEFT / RIGHT) JOIN ... ON 多表的连接条件
(LEFT / RIGHT) JOIN ... ON ...
WHERE 不包含聚合函数的过滤条件
GROUP BY ......
HAVING 包含聚合函数的过滤条件
ORDER BY ......(ASC / DESC)
LIMIT ......
(三)SQL语句的执行过程
FROM ...... --> ON --> (LEFT / RIGHT JOIN) --> WHERE --> GROUP BY --> HAVING --> SELECT --> DISTINCT(去重) --> ORDER BY(排序) --> LIMIT(分页显示)