1. 聚合函数基础从统计到分组在数据库操作中聚合函数是我们进行数据统计和分析的利器。常见的聚合函数包括COUNT()、SUM()、AVG()、MAX()和MIN()它们分别用于计数、求和、平均值、最大值和最小值的计算。1.1 五大核心聚合函数详解COUNT()函数可能是最常用的聚合函数了。它不仅能够统计所有行数还能统计特定列的非NULL值数量。在实际项目中我经常使用COUNT(DISTINCT column_name)来统计唯一值的数量这在用户去重统计时特别有用。-- 统计员工总数 SELECT COUNT(*) FROM employees; -- 统计不同部门的数量 SELECT COUNT(DISTINCT department_id) FROM employees;SUM()函数用于计算数值列的总和。在处理财务数据时SUM()几乎每天都会用到。需要注意的是如果列中包含NULL值SUM()会自动忽略它们。-- 计算所有员工的薪资总和 SELECT SUM(salary) FROM employees;AVG()函数计算平均值但有个细节容易被忽视它也会自动忽略NULL值。如果需要将NULL视为0参与计算得先用COALESCE()或IFNULL()函数处理。-- 计算平均薪资忽略NULL SELECT AVG(salary) FROM employees; -- 将NULL视为0计算平均 SELECT AVG(COALESCE(salary, 0)) FROM employees;MAX()和MIN()函数分别找出列中的最大值和最小值。它们不仅适用于数值类型还可以用于日期和字符串。-- 找出最早和最晚的入职日期 SELECT MIN(hire_date), MAX(hire_date) FROM employees;1.2 聚合函数的NULL处理机制NULL在聚合函数中的处理方式是个容易踩坑的地方。几乎所有聚合函数都会自动忽略NULL值但COUNT(*)是个例外——它统计的是行数包括NULL值所在的行。这个区别在实际项目中经常导致统计结果的偏差。提示当需要明确区分0和没有数据时考虑使用COALESCE(SUM(column), 0)来确保总是返回一个数值。2. GROUP BY的艺术数据分组的精髓GROUP BY子句是SQL中最强大的功能之一它让我们能够按照一个或多个列对结果集进行分组。但很多初学者在使用时容易混淆GROUP BY和WHERE的执行顺序。2.1 单列与多列分组单列分组是最基础的形式比如按部门统计员工数量SELECT department_id, COUNT(*) FROM employees GROUP BY department_id;多列分组则提供了更细粒度的分析能力。例如我们可能想同时按部门和职位统计SELECT department_id, job_id, COUNT(*), AVG(salary) FROM employees GROUP BY department_id, job_id;这里有个重要的细节GROUP BY子句中列的顺序会影响结果的组织方式但不会影响最终的数据内容。把department_id和job_id交换位置得到的数据是一样的只是显示顺序不同。2.2 GROUP BY的执行原理理解GROUP BY的执行原理对写出高效的查询很重要。数据库引擎处理GROUP BY时通常会按照以下步骤根据FROM和WHERE子句获取基础数据按照GROUP BY指定的列对数据进行排序和分组对每个分组应用聚合函数返回结果集这个过程中排序操作通常是性能瓶颈。在MySQL 8.0中如果GROUP BY的列上有合适的索引优化器可能会使用松散索引扫描来提高性能。2.3 分组后的排序技巧分组后的结果默认是按照分组列的升序排列的但我们可以用ORDER BY来控制排序SELECT department_id, COUNT(*) as emp_count FROM employees GROUP BY department_id ORDER BY emp_count DESC;在实际项目中我经常遇到需要按聚合结果排序的需求。一个小技巧是在ORDER BY中可以使用列的别名如上面的emp_count也可以直接使用聚合函数表达式如ORDER BY COUNT(*) DESC。3. HAVING子句分组后的过滤器HAVING子句是GROUP BY的黄金搭档它允许我们对分组后的结果进行过滤。很多初学者容易混淆HAVING和WHERE的区别其实关键在于执行时机WHERE在分组前过滤行HAVING在分组后过滤组。3.1 HAVING与WHERE的关键区别假设我们要找出平均薪资超过10000的部门SELECT department_id, AVG(salary) as avg_salary FROM employees GROUP BY department_id HAVING AVG(salary) 10000;这个查询中WHERE子句不能替代HAVING因为我们需要的是对分组后的聚合结果进行过滤而不是对原始数据进行过滤。3.2 HAVING的进阶用法HAVING不仅可以用于简单的条件过滤还能结合多个条件-- 找出员工数超过5人且平均薪资超过8000的部门 SELECT department_id, COUNT(*), AVG(salary) FROM employees GROUP BY department_id HAVING COUNT(*) 5 AND AVG(salary) 8000;在复杂查询中HAVING条件可以引用多个聚合函数-- 找出薪资差异较大的部门标准差超过平均薪资的30% SELECT department_id, AVG(salary) as avg_salary, STDDEV(salary) as salary_stddev FROM employees GROUP BY department_id HAVING STDDEV(salary) AVG(salary) * 0.3;3.3 HAVING的性能考量HAVING子句是在数据库完成所有分组和聚合计算后才应用的这意味着它不会减少聚合操作的工作量。对于大数据集先使用WHERE减少参与分组的数据量再用HAVING过滤结果通常会更高效-- 优化版先过滤再分组 SELECT department_id, AVG(salary) FROM employees WHERE salary 5000 -- 先过滤掉低薪记录 GROUP BY department_id HAVING AVG(salary) 10000;4. 实战中的常见问题与解决方案在实际项目中使用聚合函数和分组时会遇到各种边界情况和性能问题。这里分享几个我积累的经验和解决方案。4.1 Expression #N of SELECT list is not in GROUP BY clause错误这是MySQL 5.7版本中常见的错误源于SQL模式的改变。当SELECT列表中的列既不在GROUP BY中也不是聚合函数时MySQL会拒绝执行查询。解决方案有三种将列添加到GROUP BY中对列使用聚合函数修改sql_mode移除ONLY_FULL_GROUP_BY-- 错误示例 SELECT department_id, employee_name, AVG(salary) FROM employees GROUP BY department_id; -- 解决方案1添加列到GROUP BY SELECT department_id, employee_name, AVG(salary) FROM employees GROUP BY department_id, employee_name; -- 解决方案2使用聚合函数 SELECT department_id, MAX(employee_name), AVG(salary) FROM employees GROUP BY department_id; -- 解决方案3修改SQL模式不推荐生产环境使用 SET SESSION sql_mode(SELECT REPLACE(sql_mode,ONLY_FULL_GROUP_BY,));4.2 分组查询的性能优化对于大型表的分组查询性能优化至关重要。以下是我总结的几个有效方法索引优化为GROUP BY和WHERE条件中的列创建复合索引减少分组列只对必要的列进行分组预先过滤先用WHERE子句减少数据量使用派生表对已过滤和限制的数据进行分组-- 使用索引优化分组查询 ALTER TABLE employees ADD INDEX (department_id, salary); -- 使用派生表优化 SELECT d.department_id, d.avg_salary FROM ( SELECT department_id, AVG(salary) as avg_salary FROM employees WHERE hire_date 2020-01-01 GROUP BY department_id ) d WHERE d.avg_salary 10000;4.3 复杂聚合ROLLUP与GROUPING SETSMySQL支持ROLLUP操作符可以生成小计和总计行-- 按部门和职位统计薪资并生成小计和总计 SELECT department_id, job_id, SUM(salary) FROM employees GROUP BY department_id, job_id WITH ROLLUP;对于更复杂的分组需求MySQL 8.0支持GROUPING SETS-- 多种分组方式的组合 SELECT department_id, job_id, location_id, SUM(salary) FROM employees GROUP BY GROUPING SETS ( (department_id, job_id), (department_id, location_id), () );这些高级分组功能在生成报表时特别有用可以避免多次查询和应用程序端的合并操作。4.4 聚合函数中的DISTINCT用法在聚合函数中使用DISTINCT可以消除重复值这在某些场景下非常有用-- 统计每个部门的不同职位数量 SELECT department_id, COUNT(DISTINCT job_id) FROM employees GROUP BY department_id; -- 计算不同客户的订单总金额每个客户只计一次最高金额订单 SELECT SUM(DISTINCT order_max) FROM ( SELECT customer_id, MAX(amount) as order_max FROM orders GROUP BY customer_id ) t;需要注意的是DISTINCT会增加计算开销在大数据集上要谨慎使用。
企业数字化 ERP 产品动态
相关推荐
五级行政区划主数据建模:编码、树形结构与变更追踪 “中国五级行政区划体系”这几个字,第一次听到的人多半觉得它是地理课本里的东西;但只要你的系统里出现过“省/市/区”三级联动下拉框,或者被收货地址校验、门店归属统计、政务数据上报这几件事折磨过一次,你就会明白它本质上是国… · 2026/11/14 0:16:19
Agent反馈回路故障排查:模型没变为何变笨? 这段时间我一直在做 Agent 的例行评估,跑完一轮回归测试后,发现一个特别诡异的现象:模型本身没有任何改动,提示词也没换,数据集也是同一份,但 Agent 的综合得分一次比一次低。尤其是一些曾经稳定通过的基础… · 2026/11/13 23:01:56
基于KOV与依赖图的联动规则组件设计与实现 做中后台表单和流程配置的同学应该都有过这种经历:业务方跑过来说“这个字段选了 A,下面那几个就不要再填了;选了 B,金额输入框必须出现,而且默认带出上一步的值”。你听完觉得不难,随手写了几个if… · 2026/11/14 12:35:08
陇南初级电工证过期了怎么复审?含金量到底值不值? 陇南初级电工证过期了怎么复审?含金量到底值不值? 证书过期了不知道怎么复审延期,这事儿真不是小事。很多电工朋友在拿到陇南初级电工证后,工作几年后发现证书快到期了,但对复审流程一无所知,导致证书失效,影响工作和晋升机会。尤其是对应届工程类毕业… · 2026/11/14 19:16:38
武汉电工证复审微信号怎么选?含金量高的机构怎么找 武汉电工证复审微信号怎么选?含金量高的机构怎么找 怕考不过白交培训费?这是很多想报考或复审电工证的朋友心里最担心的事。尤其是在武汉,电工证复审微信号成了不少人的“救命稻草”,但怎么选一个靠谱的机构,怎么避免交了钱却拿不到证,是很多人心里的坎… · 2026/11/14 19:16:38
电工证有实体的证吗保姆级教程:证书过期了不知道怎么复审延期 电工证有实体的证吗保姆级教程:证书过期了不知道怎么复审延期 你是不是也遇到过这种情况:电工证眼看就要过期了,但你压根不知道怎么去复审?是不是每次看到“电工证有实体的证吗”这样的问题,心里都有点发慌?别急,这正是咱们今天要解决的问题。作为在应… · 2026/11/14 19:16:38
上海高压电工证挂失怎么办?不知道去哪报名怕被中介坑?值不值得考? 上海高压电工证挂失怎么办?不知道去哪报名怕被中介坑?值不值得考? 你是不是正在为【上海高压电工证挂失】的事情发愁?不知道去哪里处理,怕被中介坑,更担心这证值不值得考?其实,你不是一个人,很多刚接触这个行业的人都有类似的困惑。别急,本文就从一… · 2026/11/14 19:16:38
酒泉有电工证的怎么网上查询?工地太忙根本没时间复习考试 酒泉有电工证的怎么网上查询?工地太忙根本没时间复习考试 工地太忙根本没时间复习考试,这是很多一线电工的真实写照,尤其是像酒泉这样的施工项目密集区域,工人们常常在赶工期和休息之间挣扎。而如果你手里没有电工证,别说接活,连进场都成问题。别急,这… · 2026/11/14 19:16:38
低压电工证没有ic卡,现在考还来得及?良心建议在这里 低压电工证没有ic卡,现在考还来得及?良心建议在这里 你是不是正在找电工类工作,但发现低压电工证没有ic卡,心里打鼓,担心这个证是不是不能用了?别急,这不是你一个人的困惑,很多和你一样准备入行的工人,都遇到过这个问题。今天就从… · 2026/11/14 19:15:38
电工证丢失还能补吗?千万别踩坑,丢了证等于失业 电工证丢失还能补吗?千万别踩坑,丢了证等于失业 你正在找工作,但手里的电工证突然丢了,这下怎么办?别急,先别慌, 电工证丢失还能补吗 ?答案是肯定的,但 千万别踩坑 ,补办流程如果不了解,可能会耽误你上岗、甚至影响到你的收入。… · 2026/11/13 22:30:50
电力电缆作业证直播报名入口与办理流程良心建议 电力电缆作业证直播报名入口与办理流程良心建议 你是不是也担心学历不高报不了名?别急,今天就给你讲讲 电力电缆作业证直播 的报名流程和那些你必须知道的干货, 良心建议 在这里,别错过。 电力电缆作业证直播报名需要什么条件?… · 2026/11/14 13:23:47
英德电工证报考费多少钱,怕考不过白交培训费?看完这篇别再踩坑 英德电工证报考费多少钱,怕考不过白交培训费?看完这篇别再踩坑 怕考不过白交培训费?英德电工证报考费多少钱,你真的了解吗?现在市面上培训机构五花八门,价格参差不齐,很多人一不小心就花了冤枉钱,结果还考不过。别急,今天就来给你说清楚英德电工证的… · 2026/11/14 13:20:59
有初级电工证怎么工作 2026河南最新政策怎么应对 有初级电工证怎么工作 2026河南最新政策怎么应对 之前考的证在外省能不能转过来?这个问题我每天被问上百次。2026年河南最新政策对证书跨省转移有了明确说明,特别是南阳市的从业者,需要特别关注。… · 2026/11/14 0:00:31
电工证过期了不知道怎么复审?考电工证自学书+官方报名入口全攻略 电工证过期了不知道怎么复审?考电工证自学书+官方报名入口全攻略 证书过期了不知道怎么复审延期?很多人遇到这种情况,要么是工作太忙没时间处理,要么是不知道具体流程,导致证书失效,影响工作和项目进展。其实复审并不难,关键是要找准官方报名入口,掌… · 2026/11/14 0:00:31
为什么要低压电工证实操考试考什么 为什么低压电工证值不值得考?别再被中介骗了 你是不是也经常看到网上有人在问“低压电工证到底值不值得考”?或者在找报名点时,担心被中间人骗钱?这些问题,我懂,我也经历过。作为一名在应急管理行业摸爬滚打多年的从业者,我深知低压电工证不仅是一个从… · 2026/11/14 0:00:31
双极步进电机控制实战:DRV8818PWPR与PIC18F86K22驱动调试 /* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views … · 2026/11/13 6:12:21
STM32F207ZG + DRV8818PWPR 步进电机驱动实战解析 /* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views … · 2026/11/13 6:11:51
DRV8818PWPR+dsPIC30F4013工业级双极步进电机控制方案 /* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views … · 2026/11/13 22:31:30