SQL中group by问题

在使用sql语句中,我们常常使用group by加聚合函数来分组并聚合,从而实现某些需求。然而,不正确地使用group by和聚合函数,会带来非常隐晦的问题。

有这样一个需求:对表进行分组后找出用户首次获得最高分数的那条记录的全部信息。

为此,我创建了一张记录用户闯关信息的表,记录了用户在不同课程领域的不同关卡下获得的分数信息:

最开始我觉得很简单,sql是这样写的:

select pl.id, pl.user_id, pl.course_id, pl.pass_id, max(pl.total_score)
from pass_log pl
group by pl.user_id, pl.course_id, pl.pass_id;

结果是这样的:

大家发现端倪没有?分组和聚合的结果都是对的,但是id却是错的,正确的id应该分别是3、5啊!但是为什么取的是1、4呢?因为它取的是分组后的第一条记录的id!那应该怎么改过来呢?我的想法是先获取分组后的信息和最高分,再和原表进行内关联:

select p.id, p.user_id, p.course_id, p.pass_id, p.total_score
from pass_log p
join (
    select pl.user_id, pl.course_id, pl.pass_id, max(pl.total_score) maxTotalScore
    from pass_log pl
    group by pl.user_id, pl.course_id, pl.pass_id) t
on p.user_id = t.user_id and p.course_id = t.course_id and p.pass_id = t.pass_id
where p.total_score = maxTotalScore
group by p.user_id, p.course_id, p.pass_id;

我在最外层又加group by的原因是用户可能在同一个关卡里获得多次最高分,而我只想要首次获得最高分数的那条记录,最后结果是正确的,如图:

后来我想数据查出来的都是错的,为什么mysql不报错呢?这样不是坑我?后来发现还真的会出现报错的情况,执行sql观察:

select @@global.sql_mode;

如果结果中含有ONLY_FULL_GROUP_BY的话,执行我的第一条sql语句就会报错,想要不报错的话就要把pl.id改为any_value(pl.id),但是结果还是取分组后的第一个id,并不是我想要的结果。

其实我最后想表达的是,如果你的group by语句在一个环境下没问题,但是在其它环境下就报异常,那会不会是你group by用错了?

原文地址:https://www.cnblogs.com/liuzhulin/p/12229976.html

时间: 2024-10-09 19:46:49

SQL中group by问题的相关文章

SQL中Group By的使用

SQL中Group By的使用 1.概述 “Group By”从字面意义上理解就是根据“By”指定的规则对数据进行分组,所谓的分组就是将一个“数据集”划分成若干个“小区域”,然后针对若干个“小区域”进行数据处理. 2.原始表 3.简单Group By 示例1 select 类别, sum(数量) as 数量之和 from A group by 类别 返回结果如下表,实际上就是分类汇总. 4.Group By 和 Order By 示例2 select 类别, sum(数量) AS 数量之和 fr

sql中group by 和having 用法解析

--sql中的group by 用法解析:-- Group By语句从英文的字面意义上理解就是“根据(by)一定的规则进行分组(Group)”.--它的作用是通过一定的规则将一个数据集划分成若干个小的区域,然后针对若干个小区域进行数据处理.--注意:group by 是先排序后分组:--举例子说明:如果要用到group by 一般用到的就是“每这个字” 例如说明现在有一个这样的表:每个部门有多少人 就要用到分组的技术select DepartmentID as '部门名称',COUNT(*) a

sql中group by使用(转发)

1.概述 2.原始表 3.简单Group By 4.Group By 和 Order By 5.Group By中Select指定的字段限制 6.Group By All 7.Group By与聚合函数 8.Having与Where的区别 9.Compute 和 Compute By 1.概述 “Group By”从字面意义上理解就是根据“By”指定的规则对数据进行分组,所谓的分组就是将一个“数据集”划分成若干个“小区域”,然后针对若干个“小区域”进行数据处理. 2.原始表 3.简单Group

MYSQL:SQL中Group By的使用

1.概述 "Group By"从字面意义上理解就是根据"By"指定的规则对数据进行分组,所谓的分组就是将一个"数据集"划分成若干个"小区域",然后针对若干个"小区域"进行数据处理. 2.原始表 3.简单Group By 示例1 select 类别, sum(数量) as 数量之和 from A group by 类别 返回结果如下表,实际上就是分类汇总. 4.Group By 和 Order By 示例2

SQL中Group By 的使用

1.概述 “Group By”从字面意义上理解就是根据“By”指定的规则对数据进行分组,所谓的分组就是将一个“数据集”划分成若干个“小区域”,然后针对若干个“小区域”进行数据处理. 2.原始表 3.简单Group By 示例1 select 类别, sum(数量) as 数量之和 from A group by 类别 返回结果如下表,实际上就是分类汇总. 4.Group By 和 Order By 示例2 select 类别, sum(数量) AS 数量之和 from A group by 类别

[数据库]SQL中Group By 的常见使用方法.

前言今天逛java吧看到了一个面试题, 于是有了今天这个文章, 回顾下Group By的用法.题目如下:Select name from table group by name having count(*) = 10; 解释: 根据(by)一定的规则进行分组(Group) 所以就是根据题中的name进行分组, 然后把name相同的数量为10的记录都查找出来. 示例:表结构:执行结果: 如果再添加一条记录: wangmeng. 那么 就查询不到了. 只有 相同username count 为10

SQL 中GROUP BY 、ROLLUP、CUBE 关系和区别

转自:http://www.cnblogs.com/dyufei/archive/2009/11/12/2573974.html 不言自明,看SQL就完全理解了,不需要过多解释,不错,分享之: ROLLUP 运算符生成的结果集类似于 CUBE 运算符生成的结果集. 下面是 CUBE 和 ROLLUP 之间的具体区别: CUBE 生成的结果集显示了所选列中值的所有组合的聚合. ROLLUP 生成的结果集显示了所选列中值的某一层次结构的聚合. ROLLUP 优点: (1)ROLLUP 返回单个结果集

一.oracle的SQL中group by使用的情况(与聚合函数的关系)

SELECT r.industry_1,r.industry_2,r.agent_id,r.agent_name,COUNT(DISTINCT r.customer_name_a)数据总量,COUNT(DISTINCT CASE WHEN r.ifhs='Y' THEN r.customer_name_a END)海关数据量,COUNT(DISTINCT CASE WHEN r.ifgjh='Y'THEN r.customer_name_a END)广交会数据量,COUNT(DISTINCT C

SQL中group by 与 compute by

group by 使用group by子句联合集合函数分组查询: group by 用于对结果集分组异对,每组数段进行汇总. 语法格式: group by  列名 [having  条件表达式] 它是按指定的列进行分组,将该列相同的记录组成一组,对每组进行计算,having 则是把分组的记录加以过滤,where 子句里在汇总之前加以过滤. 注意:select 语句中显示的列是参加计算的列和 group by 子句中有的列. 例: select egg_liang , count (egg_jia