分组统计查询
统计函数(分组函数)
count函数的主要作用是统计一张数据表之中数据量的个数。与它功能类似的常用函数有五个:
- COUNT():计数,根据表中实际的数据量返回结果;
- SUM():求和,针对数字的统计;
- AVG():平均值,针对数字的统计;
- MIN():最小值,支持各种数据类型;
- MAX():最大值,支持各种数据类型;
范例:
SELECT COUNT(*) 人数, AVG(sal) 员工平均工资, SUM(sal) 每月总支出, MAX(sal) 最高工资, MIN(sal) 最低工资
FROM EMP;
- 这些函数都支持嵌套。
- 当表中没有数据时,只有COUNT()函数会返回值(0),而其他四个都返回NULL。
COUNT()的三种使用方式
- COUNT(*):返回表中的全部记录数;
- COUNT(字段):返回表中指定字段的记录数;
- COUNT(DISTINCT 字段):返回消除重复数据之后的字段记录数。
分组统计(GROUP BY)
根据部门编号分组,查询出每个部门的编号、人数、平均工资,并按平均工资排序。
SELECT DEPTNO, COUNT(*), AVG(SAL)
FROM EMP
GROUP BY DEPTNO
ORDER BY AVG(SAL) DESC;
ORDER BY放置在GROUP BY子句后。
使用注意
- 如果查询不使用GROUP BY子句,那么SELECT子句中只允许出现统计函数;
- 如果查询中使用了GROUP BY子句,那么SELECT子句中只允许出现分组字段、统计函数;
- 统计函数允许嵌套,但是嵌套之后的SELECT子句里只允许出现嵌套函数,不允许出现任何字段。
多表查询与分组统计
单子段分组
查询每个部门的名称、部门人数、平均工资:
SELECT D.DNAME, COUNT(E.EMPNO), AVG(E.SAL)
FROM EMP E, DEPT D
WHERE E.DEPTNO(+) = D.DEPTNO
GROUP BY D.DNAME;
多字段分组
查询出每个部门的编号、名称、位置、部门人数、平均工资:
SELECT D.DEPTNO, D.DNAME, D.LOC, COUNT(E.EMPNO), AVG(E.SAL)
FROM EMP E, DEPT D
WHERE E.DEPTNO(+) = D.DEPTNO
GROUP BY D.DEPTNO, D.DNAME, D.LOC;
总结
对比以上单子段分组与多字段分组可以发现,查询中使用了GROUP BY子句,那么SELECT子句中只允许出现分组字段、统计函数;所以查询中的除统计函数以外,其他字段都必须出现在GROUP BY中。
分组过滤HAVING
概念
由于GROUP BY在WHERE子句之后执行,所以无法再WHERE条件中进行统计条件的限定。而可以使用HAVING实现对分组过后的数据进行过滤。
HAVING只能不出现或与GROUP BY成对出现。
实例
查询出每个职位的名称,职位的平均工资大于2000:
SELECT JOB, AVG(SAL)
FROM EMP
GROUP BY JOB
HAVING AVG(SAL) > 2000;
WHERE与HAVING 的区别
- WHERE子句是在GROUP BY 分组之前进行筛选,用于选出可以用于分组的数据,并且WHERE子句中不允许使用统计函数。
- HAVING子句实在GROUP BY分组之后执行的,所以可以使用统计函数。