MySQL-聚合函数
什么是聚合函数聚合函数作用于一组数据,并对一组数据返回一个值.聚合函数的类型AVG() 平均值SUM() 求和MAX() 最大值MIN() 最小值COUNT() 计数 不计算NULL值计算表中有多少条记录COUNT(*) COUNT(1)如果需要统计表中的记录数,使用COUNT(*),COUNT(1),COUNT(具体字段)哪个效率更高呢对于MyISAM引擎的表是没有区别的,这种引擎内部有一计数器在维护着行数,时间复杂度都是O(1)Innodb引擎的表用conut(*)count(1)直接读行数,复杂度是O(n).因为Innodb真的要去数一遍,但好于count(列名)GROUP BY的使用查询各个部门的平均工资,最高工资SELECT department_id,AVG(salary) FROM employees GROUP BY department_id;查询各个job_id的平均工资SELECT job_id,AVG(salary) FROM employees GROUP BY job_id;使用多个列分组查询各个department_id,job_id的平均工资SELECT job_id,AVG(salary) FROM employees GROUP BY job_id;注意:1.SELECT中出现的非组函数的字段必须声明在GROUP BY中.反之,GROUP BY中声明的字段可以不出现在SELECT中.2.GROUP BY 声明在FROM后,WHERE后,BRDER BY前面,LIMIT前面3.GROUP BY中使用WITH ROLLUP(不能和ORDER BY一起使用)当使用ROLLUP时,不能同时使用ORDER BY字句进行结果排序,即ROLLUP和ORDER BY是互相排斥的SELECT department_id,AVG(salary) FROM employees GROUP BY department_id WITH ROLLUP;HAVING的使用作用:用来过滤数据要求:1.如果过滤条件中使用了聚合函数,则必须使用HAVING来替换WHERE,否则报错2.HAVING必须声明在GROUP BY的后面3.开发中,我们使用HAVING的前提是SQL中使用了GROUP BY.查询各个部门中最高工资比10000高的部门信息SELECT department_id, MAX(salary) FROM employees GROUP BY department_id HAVING MAX(salary) 10000;查询部门ID为10,20,30,40这四个部门中最高工资比10000高的部门信息方式1:(推荐,执行效率高于方式2)SELECT department_id, MAX(salary) FROM employees WHERE department_id IN (10, 20, 30, 40) GROUP BY department_id HAVING MAX(salary) 10000;方式2:SELECT department_id, MAX(salary) FROM employees GROUP BY department_id HAVING MAX(salary) 10000 AND department_id IN (10, 20, 30, 40);结论当过滤条件中有聚合函数时则此过滤条件必须声明在HAVING中当过滤条件中没有聚合函数时则此过滤条件声明在WHERE中或HAVING中都可以但是建议声明在WHERE中WHERE与HAVING的对比区别1WHERE可以直接使用表中的字段作为筛选条件但不能使用分组中的计算函数作为筛选条件HAVING必须要与GROUP BY配合使用可以把分组计算的函数和分组字段作为筛选条件。这决定了需要对数据进行分组统计的时候HAVING可以完成WHERE不能完成的任务这是因为在查询语句中WHERE在GROUP BY之前所以无法对分组结果进行筛选HAVING在GROUP BY之后可以使用分组字段和分组中的计算函数对分组的结果集进行筛选这个功能是WHERE无法完成的。另外WHERE排除的记录不再包括在分组中。区别2如果需要连接从关联表中获取需要的数据WHERE是先筛选后连接而HAVING是先连接后筛选这一点就决定了在关联查询中WHERE必HAVING更高效。因为WHERE可以先筛选用一个筛选后较小的数据集合关联表进行连接这样占用的资源比较少执行效率也比较高。HAVING则需要先把结果集准备好也就是用未被筛选的数据集进行关联然后对这个大的数据集进行筛选这样占用的资源就比较多执行效率也比较低。SQL底层执行原理SELECT语句完整结构sql92语法:SELECT ...,...,...(存在聚合函数)FROM ...,...,...WHERE 多表的连接条件 AND 不包含聚合函数的过滤条件GROUP BY ...,...HAVING 包含聚合函数的过滤条件ORDER BY ...,... (ASC/DESC)LIMIT ...,...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