Mysql使用实际01---SQL分组查询;having 和 where 的区别

1.SQL分组查询使用场景

对记录的分组是通过关键字 GROUP BY 实现的, GROUP BY 后面跟着一个定义组的构成的属性列表。 如果我们使用语句 GROUP BY A1,……, Ak 我们就把记录分成了组,这样当且仅当两条记录 在所有属性 A1,……, Ak 上的值达成一致,它们才是同一组的。 SQL 允许我们把一个表里面的记录用GROUP BY 分成组。

分组查询通常用于配合聚合函数,达到分类汇总统计的信息。

group by,顾名思义即为分组,即将原来的一整块数据分成几小块。分组是聚合的前提,聚合是在每个分组内进行一些统计,如在分组内的最大值,最小值,平均值,个数等。

下表列出了SQL的执行顺序:

子句说明使用场景
select 查询数据 在db数据检索时使用
from 检索的表 检索时使用
where 过滤数据的条件 需要对数据进行筛选时
group by 分组select的结果集 需要聚合统计时常用
having 过滤分组 对分组进行过滤时需要
order by 排序结果集 需要按照某种顺序展示数据

 

新建employee表:

复制代码
/*
 Navicat Premium Data Transfer

 Source Server         : test01
 Source Server Type    : MySQL
 Source Server Version : 50723
 Source Host           : localhost:3306
 Source Schema         : flep

 Target Server Type    : MySQL
 Target Server Version : 50723
 File Encoding         : 65001

 Date: 17/08/2022 18:37:18
*/

SET NAMES utf8mb4;
SET FOREIGN_KEY_CHECKS = 0;

-- ----------------------------
-- Table structure for employee
-- ----------------------------
DROP TABLE IF EXISTS `employee`;
CREATE TABLE `employee`  (
  `id` int(11) NOT NULL,
  `name` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_bin NULL DEFAULT NULL,
  `gender` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_bin NULL DEFAULT NULL,
  `salary` int(11) NULL DEFAULT NULL,
  `deparmant` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_bin NULL DEFAULT NULL,
  PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8mb4 COLLATE = utf8mb4_bin ROW_FORMAT = Dynamic;

-- ----------------------------
-- Records of employee
-- ----------------------------
INSERT INTO `employee` VALUES (1, '张三', '', 2000, '    营销部');
INSERT INTO `employee` VALUES (2, '李四', '', 4000, '营销部');
INSERT INTO `employee` VALUES (3, '王五', '', 1000, '研发部');
INSERT INTO `employee` VALUES (4, '赵六', '', 8000, '财务部');
INSERT INTO `employee` VALUES (5, '孙七', '', 5000, '研发部');
INSERT INTO `employee` VALUES (6, '周八', '', 6000, '人事部');
INSERT INTO `employee` VALUES (7, '吴九', '', 8000, '研发部');
INSERT INTO `employee` VALUES (8, '郑十', '', 4000, '人事部');

SET FOREIGN_KEY_CHECKS = 1;
复制代码

2.SQL分组查询Group By+Group_concat

group by 是分组,分组并不是去重,而是分组;

将查询结果按一个或多个进行分组,字段值相同的为一组;

分组查询中,select后只能跟分组的字段和聚合函数

(1)Group By+Group_concat : 表示分组之后,根据分组结果,使用 group_contact() 来放置每一组的每字段的值的集合。

select deparmant, GROUP_CONCAT(`name`) from employee GROUP BY deparmant

根据 department 分组,通过 group_concat('name'),查看每组里面的姓名都有哪些

(2)案例2

SELECT gender,GROUP_CONCAT(`name`) from employee GROUP BY gender

3.SQL分组+聚合函数

3.1 根据department 分组,计算各部门下工资总数,平均工资,最高工资

select deparmant, GROUP_CONCAT(salary), SUM(salary),AVG(salary) 平均工资,MAX(salary) 最高工资 from employee GROUP BY deparmant;

3.2 查询每个部门的部门名称以及每个部门的人数

SELECT deparmant, GROUP_CONCAT(`name`), COUNT(*) from employee GROUP BY deparmant

3.SQL分组GroupBy+Having

  • group by + having 用来分组查询后指定一些条件来输出查询结果
  • having 和 where 一样,但 having 只能用于 group by

3.1 查询工资总和大于 9000的部门名称

SELECT deparmant, GROUP_CONCAT(salary), SUM(salary) FROM employee 
GROUP BY deparmant 
HAVING SUM(salary) > 9000;

having 和 where 的区别:

  • having 是在分组后对数据进行过滤,where 是在分组前对数据进行过滤
  • having后面可以使用分组函数(统计函数),where后面不可以使用分组函数
  • where 是对分组前记录的条件,如果某行记录没有满足where字句的条件,那么这行记录不会参加分组;而having是对分组后数据的约束

3.2 查询工资大于2000的,工资总和大于9000的部门名称以及工资和

select deparmant,GROUP_CONCAT(salary), SUM(salary) from employee 
WHERE salary > 2000 
GROUP BY deparmant 
HAVING sum(salary) > 9000
ORDER BY SUM(salary) DESC;

参考文献: https://www.cnblogs.com/friday69/p/9389720.html

posted @   雨后观山色  阅读(326)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· 分享4款.NET开源、免费、实用的商城系统
· 全程不用写代码,我用AI程序员写了一个飞机大战
· MongoDB 8.0这个新功能碉堡了,比商业数据库还牛
· 白话解读 Dapr 1.15:你的「微服务管家」又秀新绝活了
· 上周热点回顾(2.24-3.2)
历史上的今天:
2021-08-17 Java Springcloud项目bug记录过程01
2021-08-17 TiDB学习笔记02-场景案例综述
点击右上角即可分享
微信分享提示