目录
聚合查询
聚合函数
GROUP BY子句
HAVING
联合查询
内连接
外连接
自连接
子查询
单行子查询
多行子查询
合并查询
聚合查询
聚合函数
首先创建一个学生表,用来演示聚合函数的作用
-- 创建学生表
drop table if exists student;
create table student(
id int primary key auto_increment,
sname varchar(20) not null,
math decimal(5,2),
english decimal(5,2),
chinese decimal(5,2)
);
对其中插入若干列数据,插入后的student表为
常见的统计总数、计算平均值等操作,可以使用聚合函数来实现,常见的聚合函数有:
· count(某个字段):获取整个结果集的行数.
count(某个字段) = count(*) = count(常数).
例如:
-- 统计班级内有多少同学
select count(*) from student;
· sum(某个字段):将结果集,这个字段求和计算
-- 统计数学成绩总分
select sum(math) from student;
· avg(某个字段):将结果集,这个字段求平均值计算
-- 统计平均总分
select avg(math + english + chinese) 平均总分 from student;
· max(某个字段): 将结果集,这个字段取最大值
-- 返回英语分数的最大值
select max(english) from student;
· min(某个字段):将结果集,这个字段取最小值
-- 返回英语分数大于100分的最小值
select min(english) from student where english > 100;
GROUP BY子句
select中使用group by子句可以对指定列进行分组查询.需要满足:使用group by进行分组查询时,select指定的字段必须是“分组依据字段”,其他字段若想出现在select中则必须包含在聚合函数中.
语法:
select xxx, max(xxx), ... from 表名 group by xxx;
· 首先准备测试表
-- 准备测试表
create table emp(
id int primary key auto_increment,
name varchar(20) not null,
role varchar(20) not null,
salary numeric(11,2)
);
· 插入测试数据
-- 插入测试数据
insert into emp(name, role, salary) values
('张三', '游戏代练', 14256.32),
('李四', '游戏代练', 24256.32),
('ppq', '娱乐主播', 64256.32),
('高迪', '娱乐主播', 54256.32),
('王五', '游戏代练', 14256.32),
('赵某', '工作室董事长', 104256.32);
· group by子句的使用示例
查询每个职业的最高工资、最低工资和平均工资
-- 查询每个职业的最高工资、最低工资和平均工资
select role, max(salary), min(salary), avg(salary) from emp group by role;
HAVING
group by子句进行分组后,需要对分组结果再进行条件筛选,不能使用where语句而需要用到having来对其进行筛选.
· having的使用示例
①显示平均工资低于100000的角色和它的平均工资
-- 显示平均工资低于100000的角色和它的平均工资
select role, avg(salary) from emp group by role having avg(salary) < 100000;
联合查询
笛卡尔积
实际开发中往往数据来源于不同的表,所以需要多表联合查询,多表联合查询是对多张表的数据取笛卡尔积,例如下列所示的两张表取笛卡尔积
· 首先建立四张表,分别为:班级表、学生表、课程表、中间表(学生课程考试成绩表)
建表代码已上传至gitee中:点击查看代码
· 再分别对建好的表中进行插入数据,具体代码已上传至gitee代码仓库中,链接在上面.
· 班级表数据
· 学生表数据
· 课程表数据
· 中间表数据(考试成绩表)
中间表插入的数据较多,8名学生,6门课程,公48条记录,这里只展示部分数据
所有的初始操作已完成,下来进行各种联合查询的演示
内连接
· 语法
select 字段 from 表1 别名1 [inner] join 表2 别名2 on 连接条件 and 其他条件;
select 字段 from 表1 别名1,表2 别名2 where 连接条件 and 其他条件;
· 查询张三同学的成绩
-- 查询张三的成绩
select sco.score from student stu inner join exam_score sco
on stu.id = sco.student_id and stu.name = '张三';
· 查询所有同学总成绩和同学的个人信息
-- 查询所有同学总成绩和同学的个人信息
select
stu.name,
sum(sco.score)
from
student stu
inner join exam_score sco on stu.id = sco.student_id
group by
sco.student_id;
外连接
外连接分为左外连接和右外连接,如果联合查询,左侧的表完全显示我们就说是左外连接;右侧的表完全显示我们就说是右连接.
· 语法
-- 左外连接,表1完全显示
select 字段名 from 表名1 left join 表名2 on 连接条件;
-- 右外连接,表2完全显示
select 字段 from 表名1 right join 表名2 on 连接条件;
· 查询所有同学的成绩及个人信息
-- 查询所有同学的成绩及个人信息
select
stu.id,
stu.name,
sco.score,
sco.course_id,
cou.name
from
student stu
left join exam_score sco on stu.id = sco.student_id
left join course cou on sco.course_id = cou.id
order by
stu.id;
共48条数据,只展示部分数据
自连接
自连接是指在同一张表连接自身进行查询.
· 显示所有”Java“成绩比”高等数学A“成绩高的成绩信息
-- 显示所有”Java“成绩比”高等数学A“成绩高的成绩信息
select
stu.*,
s1.score 数据库原理,
s2.score Java
from
exam_score s1
join exam_score s2 on s1.student_id = s2.student_id
join student stu on s1.student_id = stu.id
join course c1 on s1.course_id = c1.id
join course c2 on s2.course_id = c2.id
and s1.score < s2.score
and c1.name = '数据库原理'
and c2.name = 'Java';
子查询
子查询是指嵌入在其他sql语句中的select语句,也叫嵌套查询
单行子查询
单行子查询返回一行记录的子查询
· 查询”孙某某“同学的同班同学
-- 查询”孙某某“同学的同班同学
select * from student where classes_id = (select
classes_id from student where name = '孙某某');
多行子查询
多行子查询返回多行记录的子查询
· 例如查询“Java”或“高等数学A”课程的成绩信息,可以使用in关键字,也可以使用exists关键字
· [NOT] IN关键字
-- 使用IN
select * from exam_score where course_id in (select
id from course where name = 'Java' or name = '高等数学A');
-- 使用NOT IN
select * from exam_score where course_id not in (select
id from course where name != 'Java' and name != '高等数学A');
· NOT EXISTS关键字
-- 使用EXISTS
select * from exam_score sco where exists(select sco.id from course cou
where (name = 'Java' or name = '高等数学A') and cou.id = sco.course_id);
-- 使用NOT EXISTS
select * from exam_score sco where not exists(select sco.id from course cou
where (name != 'Java' and name != '高等数学A') and cou.id = sco.course_id);
合并查询
在实际应用中,为了合并多个select的执行结果,可以使用集合操作符 union、union all.使用union或union all时,前后查询的结果集中,字段需要一致.
· UNION
该操作符用于取得两个结果集的并集。当使用该操作符时,会自动去掉结果集中的重复行.
· 查询id小于3,或者名字为“高等数学A”的课程
-- 使用union
select * from course where id < 3
union
select * from course where name = '高等数学A';
· UNION ALL
该操作符用于取得两个结果集的并集.当使用该操作符时,不会去掉结果集中的重复行.
· 查询id小于3,或者名字为“Java”的课程
-- 使用union all
-- 查询id小于3,或者名字为“Java”的课程
select * from course where id < 3
union all
select * from course where name = 'Java';
本篇博客所有代码已上传至gitee中,点击获取代码:MySQL