分组聚合
最常用的场景就是分组聚合,由多条变成比较少记录的过程是分组聚合,既然需要分组,就要考虑使用哪个字段进行分组最好,一般来说,主键才是group by 后面的分组字段
主键(PRIMARY KEY) 的完整称呼是“主键约束”,分为单字段主键和多字段联合主键,这两种主键约束都可以创建、修改和删除 使用主键应注意以下几点:
- 每个表只能定义一个主键。
- 主键值必须唯一标识表中的每一行,且不能为 NULL,即表中不可能存在有相同主- 键值的两行数据。这是唯一性原则。
- 一个字段名只能在联合主键字段表中出现一次。
- 联合主键不能包含不必要的多余字段。当把联合主键的某一字段删除后,如果剩下的字段构成的主键仍然满足唯一性原则,那么这个联合主键是不正确的。这是最小化原则。
分组聚合的过程:
如:select id, name, avg(score) as s from table group by id;
1、先分组
2、后聚合
聚合是由多变一的过程,就是每一个组变成一条记录,有聚合的取聚合的结果,没有聚合的取每个组的第一条记录,avg(score) 取每个组的成绩的平均成绩(avg是平均函数,属于聚合函数),id没有聚合,就取每个组的第一条记录,又因为每个组的id都一样,所以取一个是合理的。
only_full_group_by 模式
MySql 5.7以后的版本,默认情况下,sql_mode里默认打开only_full_group_by 模式,这个打开后,对Sql的语法检查就会很严格,如果没有使用聚合函数,使用了group by但是查询的列没有出现在group by后面就会出现这个问题。
SELECT NAME,SEX FROM TABLE GROUP BY SEX;
-- 以sex字段进行分组查询会出现报错
SELECT NAME,SEX FROM TABLE GROUP BY NAME,SEX;
-- 这样就不会报错,因为使用GROUP BY不规范
其实这样挺好的,似的SQL的写法更规范,当然也可以进行解决,规避这种错误 参考:
- https://www.cnblogs.com/zenghi-home/p/13397649.html
- https://www.jianshu.com/p/7f532985ff39
- https://zhuanlan.zhihu.com/p/296449901
DISTINCT 与 GROUP BY 比较
- distinct支持单列、多列的去重方式,单纯的去重操作使用distinct,速度是快于group by的,
- 多列的去重则是根据指定的去重的列信息来进行,即只有所有指定的列信息都相同,才会被认为是重复的信息,所以使用distinct时要注意多列问题,只能使用group by
- group by 在多列的去重方面使用的较多,但其主要还是会用来进行聚合统计的
- 性能:数据量比较大的表,关联字段都会加索引,一般来说,不管是加不加索引group by 都比distinct 快
参考:
- https://www.jb51.net/article/78000.htm
- https://www.jb51.net/article/77999.htm
- https://www.jb51.net/article/74556.htm
- https://www.jb51.net/article/182395.htm
|