13. 分组数据

news/2025/1/20 3:52:27/文章来源:https://www.cnblogs.com/hisun9/p/18514746

1. 数据分组

分组允许把数据分为多个逻辑组,以便能对每个组进行聚集计算

2. 创建分组

分组是在SELECT语句的GROUP BY子句中建立的。

比如:

select vend_id, count(*) as num_prods
from products
group by vend_id;

输出如下:

img

上面的SELECT语句指定了两个列,vend_id包含产品供应商的ID,num_prods为计算字段(用COUNT(*)函数建立)。GROUP BY子句指示MySQL按vend_id排序并分组数据。这导致对每个vend_id而不是整个表计算num_prods一次。

从输出中可以看到,供应商1001有3个产品,供应商1002有2个产品,供应商1003有7个产品,而供应商1005有2个产品。

因为使用了GROUP BY,就不必指定要计算和估值的每个组了。系统会自动完成。

GROUP BY子句指示MySQL分组数据,然后对每个组而不是整个结果集进行聚集。

在具体使用GROUP BY子句前,需要知道一些重要的规定:

  • GROUP BY子句可以包含任意数目的列。这使得能对分组进行嵌套(“GROUP BY 可以嵌套分组”是指在 GROUP BY 子句中可以指定多个列进行分组),为数据分组提供更细致的控制。

  • 如果在GROUP BY子句中嵌套了分组,数据将在最后规定的分组上进行汇总。换句话说,在建立分组时,指定的所有列都一起计算(所以不能从个别的列取回数据)。

    补充:

    “如果在 GROUP BY 子句中嵌套了分组,数据将在最后规定的分组上进行汇总”指的是在多层分组时,最终的聚合结果是基于最后一个分组条件进行汇总的。这意味着在所有指定的分组条件中,最后一个分组条件决定了最终的汇总结果。

    具体解释

    • 分组的顺序: 当你在 GROUP BY 中指定多个列时,数据库会首先按第一个列分组,然后在每个分组内再按第二个列分组,以此类推,直到最后一个列。最终的汇总是基于最后一个列。

    • 最终汇总的依据: 最后一个列的分组决定了如何计算聚合函数(如 SUM、COUNT 等)。这意味着在所有的分组中,最后一个分组的结果将是你查询返回的主要汇总信息。

  • GROUP BY子句中列出的每个列都必须是检索列或有效的表达式(但不能是聚集函数)。如果在SELECT中使用表达式,则必须在GROUP BY子句中指定相同的表达式。不能使用别名。(不太理解,总感觉有点问题,不管这条了)

    不过这样写是错的:

    img

    这样写也是错的:

    img

  • 除聚集计算语句外,SELECT语句中的每个列都必须在GROUP BY子句中给出。

  • 如果分组列中具有NULL值,则NULL将作为一个分组返回。如果列中有多行NULL值,它们将分为一组。

  • GROUP BY子句必须出现在WHERE子句之后,ORDER BY子句之前。

补充:

使用ROLLUP:

使用WITH ROLLUP关键字,可以得到每个分组以及每个分组汇总级别(针对每个分组)的值。

比如:

select vend_id, count(*) as num_prods
from products
group by vend_id with rollup;

输出如下:

img

3. 过滤分组

除了能用GROUP BY分组数据外,MySQL还允许过滤分组,规定包括哪些分组,排除哪些分组。

例如,可能想要列出至少有两个订单的所有顾客。为得出这种数据,必须基于完整的分组而不是个别的行进行过滤。

我们已经看到了WHERE子句的作用(第6章中引入)。但是,在这个例子中WHERE不能完成任务,因为WHERE过滤指定的是行而不是分组。事实上,WHERE没有分组的概念。

MySQL为此目的提供了另外的子句,那就是HAVING子句。

HAVING非常类似于WHERE。事实上,目前为止所学过的所有类型的WHERE子句都可以用HAVING来替代。唯一的差别是WHERE过滤行,而HAVING过滤分组。

补充:

  • HAVING支持所有WHERE操作符:

    在第6章和第7章中,我们学习了WHERE子句的条件(包括通配符条件和带多个操作符的子句)。所学过的有关WHERE的所有这些技术和选项都适用于HAVING。它们的句法是相同的,只是关键字有差别。

怎么过滤分组呢?请看:

select cust_id, count(*) as orders
from orders
group by cust_id
having count(*) >= 2;

输出如下:

img

最后一行增加了HAVING子句,它过滤COUNT(*) >=2(两个以上的订单)的那些分组。

注意:

  • HAVING和WHERE的差别

    这里有另一种理解方法,WHERE在数据分组前进行过滤,HAVING在数据分组后进行过滤。这是一个重要的区别,WHERE排除的行不包括在分组中。

那么,有没有在一条语句中同时使用WHERE和HAVING子句的需要呢?事实上,确实有。

假如想进一步过滤上面的语句,使它返回过去12个月内具有两个以上订单的顾客。为达到这一点,可增加一条WHERE子句,过滤出过去12个月内下过的订单。然后再增加HAVING子句过滤出具有两个以上订单的分组。

比如下面的例子,它列出具有2个(含)以上、价格为10(含)以上的产品的供应商:

select vend_id, count(*) as num_prods
from products
where prod_price >= 10
group by vend_id
having count(*) >= 2;

输出如下:

img

4. 分组和排序

GROUP BY 和 ORDER BY 是非常不同的。表13-1汇总了它们之间的差别。

img

(这个图也有点不理解,特别是第三条,不知道这个对不对)

表13-1中列出的第一项差别极为重要。我们经常发现用GROUP BY分组的数据确实是以分组顺序输出的。但情况并不总是这样,它并不是SQL规范所要求的。

此外,用户也可能会要求以不同于分组的顺序排序。仅因为你以某种方式分组数据(获得特定的分组聚集值),并不表示你需要以相同的方式排序输出。

应该提供明确的ORDER BY子句,即使其效果等同于GROUP BY子句也是如此。

解释下上面那段话是啥意思:

img

注意:

  • 不要忘记ORDER BY:

    一般在使用GROUP BY子句时,应该也给出ORDER BY子句。这是保证数据正确排序的唯一方法。千万不要仅依赖GROUP BY排序数据。

为说明GROUP BY和ORDER BY的使用方法,举个例子,它检索总计订单价格大于等于50的订单的订单号和总计订单价格:

select order_num, sum(quantity * item_price) as ordertotal
from orderitems
group by order_num
having sum(quantity * item_price) >= 50;

输出如下:

img

为按总计订单价格排序输出,需要添加ORDER BY子句,如下所示:

select order_num, sum(quantity * item_price) as ordertotal
from orderitems
group by order_num
having sum(quantity * item_price) >= 50
order by ordertotal;

img

在这个例子中,GROUP BY子句用来按订单号(order_num列)分组数据,以便SUM(*)函数能够返回总计订单价格。HAVING子句过滤数据,使得只返回总计订单价格大于等于50的订单。最后,用ORDER BY子句排序输出。

5. SELECT子句顺序

表13-2以在SELECT语句中使用时必须遵循的次序,列出迄今为止所学过的子句。

img
img

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/823942.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

什么叫做网络编程

网络编程是一种编程实践,主要关注在网络环境中进行数据交换的应用程序的开发,包括了如何使用和理解各种协议、数据传输方式和网络架构等内容,以在不同计算机或系统间实现有效的信息交换。套接字是网络编程的基础,是网络上运行的程序之间进行数据交换的一种方式。什么叫做网…

Linux进程调度器-CPU负载

1. 概述 CPU负载(cpu load)指的是某个时间点进程对系统产生的压力。来张图来类比下(参考Understanding Linux CPU Load)CPU的运行能力,就如大桥的通行能力,分别有满负荷,非满负荷,超负荷等状态,这几种状态对应不同的cpu load值; 单CPU满负荷运行时cpu_load为1,当多个…

Paimon lookup store 实现

Lookup Store 主要用于 Paimon 中的 Lookup Compaction 以及 Lookup join 的场景. 会将远程的列存文件在本地转化为 KV 查找的格式. Hash https://github.com/linkedin/PalDB Sort https://github.com/dain/leveldb https://github.com/apache/paimon/pull/3770整体文件结构:相…

研究生如何利用 ChatGPT 帮助开展日常科研工作

研究生可以利用 ChatGPT 帮助开展日常科研工作:1. 文献综述与资料查找;2. 论文写作与润色;3. 问题解答与研究思路拓展;4. 实验设计与数据分析;5. 科研计划和进度管理;6. 学术交流和论文审阅。研究生常常需要面对海量文献,ChatGPT 可以成为文献综述的得力助手。1. 文献综…

13.Java的IO流

文件 概念文件:保存数据的地方。 文件流:文件在程序中是以流的形式来操作的。 流:数据在数据源(文件)和程序(内存)之间经历的路径。输入流:数据从数据源(文件)到程序(内存)的路径。 输出流:数据从程序(内存)到数据源(文件)的路径。常用操作构造方法方法 说明F…

论文词汇积累-铁路专业术语如车务段等(在进行小论文翻译的过程中遇到的问题,搜集整理一下)

一、铁路专用英语 专业词汇中英对照翻译 来源:https://blog.csdn.net/weixin_44304362/article/details/108827567 铁路工程词汇 线路工程 railway line engineering 铁路勘测 ;铁道勘测 railway reconnaissance 铁路选线 ;铁道选线 railway route selection;railway location…

考研打卡(2)

开局(2) 开始时间 2024-10-29 19:21:57 结束时间 2024-10-29 23:32:52呜呜,昨天被老师骂了数据结构能说明快速排序是不稳定的排序方法的一组关键字序列是____(暨南大学2011) A (10,20,30,40,50) B (50,40,30,20,10) C (20,20,30,10,40) D (20,40,30,30,10)C (20,…

vue2基础组件通信案例练习:把案例Todo-list改写成本地缓存

vue2基础组件通信案例练习:把案例Todo-list改写成本地缓存@目录概述前端代码本人其他相关文章链接 概述前面文章案例已经练习了父子组件之间的通信,这一节讲述如何把todos数组放进本地缓存中,因为实际开发场景中频繁查询的数据很有可能会用到本地缓存技术。思考:如何改成使…

Webstorm 2024 安装使用 (附加永久激活码、补丁)

下载安装第二步,安装完成之后,下载补丁 下载地址(里面包含激活码)完成,之后输入激活码免责声明:本文中的资源均来自互联网,仅供个人学习和交流使用,严禁用于商业行为,下载后请在24小时内从电脑中彻底删除。对于因非法使用而引起的版权争议,与作者无关。所有资源仅供学习…

高级语言程序设计课程第五次个人作业

这个作业属于哪个课程:https://edu.cnblogs.com/campus/fzu/2024C/ 这个作业要求在哪里: https://edu.cnblogs.com/campus/fzu/2024C/homework/13298 学号:<102400229> 姓名:<杨灿> 书本第8章8.11编程练习题目中的第1题 没有问题书本第8章8.11编程练习题目中的…

代码生产力提高100倍,Claude-3.5 +Cline 打造超强代码智能体!小白也能开发各种app!

嘿,各位小伙伴们。 今天,带大家走进神奇的 AI 世界,一起探索强大的工具和技术。 最近,Anthropic 发布了全新的 Claude-3.5-sonnet 模型,这可是 Claude-3.5-sonnet 模型的升级版哦!这款最新的模型在多方面的能力都有了显著提升,尤其是在编程方面。已经完全超越 GPT 模型,…

在线协作产品有哪些

在线协作产品主要有以下四类:一、通信工具,如Slack、Microsoft Teams、Zoom;二、文件共享与协作,如Google Workspace、Dropbox、Microsoft OneDrive;三、项目管理与任务追踪,如Trello、Asana、JIRA;四、设计与创作协作,如Figma、Adobe Creative Cloud、Canva。通信工具…