【MySQL】 查询进阶 | 聚合查询 | 联合查询 | 聚合函数 | 笛卡尔积 | 内连接 | 外链接 | 自连接 | 子查询 | 合并查询

文章目录

    • 查询进阶
      • 1.聚合查询
          • 1.聚合函数
          • 2.group by 子句
          • 3.having
      • 2.联合查询
            • 笛卡尔积
        • 1.内连接
            • 查询许仙同学的成绩
            • 查询所有同学的总成绩
            • 查询所有同学的每门课程和分数:
        • 2.外连接
          • 1.内连接:
          • 2.左外连接
          • 3.右外链接
        • 3.自连接
        • 4.子查询
            • 单行子查询
            • 多行子查询
            • 查询“语文”或“英文”课程的成绩信息
            • in
        • 5.合并查询
            • union


查询进阶

1.聚合查询

表达式查询,是针对列和列之间进行运算。

聚合查询,是针对行和行之间进行运算

sql中提供了一些“聚合函数”,通过聚合函数来完成行与行之间的运算

1.聚合函数
  • 函数名后面,不能乱加空格

在这里插入图片描述

  • count() :查询结果集的行数

    ​ count得到的结果可以参与各种运算,或者搭配其他sql语句使用


mysql> select *from exam_result;
+------+--------+---------+------+---------+
| id   | name   | chinese | math | english |
+------+--------+---------+------+---------+
|    1 | 唐三藏 |    67.0 | 98.0 |    56.0 |
|    2 | 孙悟空 |    87.5 | 78.0 |    77.0 |
|    3 | 猪悟能 |    88.0 | 98.5 |    90.0 |
|    4 | 曹孟德 |    82.0 | 84.0 |    67.0 |
|    5 | 刘玄德 |    55.5 | 85.0 |    45.0 |
|    6 | 孙权   |    70.0 | 73.0 |    78.5 |
|    7 | 宋公明 |    75.0 | 65.0 |    30.0 |
+------+--------+---------+------+---------+
7 rows in set (0.00 sec)

mysql> select count(*) from exam_result;
+----------+
| count(*) |
+----------+
|        7 |
+----------+

mysql> select count(name) from exam_result;
-- 先查询到name的结果集,再判断name有几行
+-------------+
| count(name) |
+-------------+
|           7 |
+-------------+

mysql> insert into exam_result values(null,null,null,null,null);
-- 插入一行空数据后
Query OK, 1 row affected (0.00 sec)

mysql> select count(*) from exam_result;
-- null也占一行,进行统计 
+----------+
| count(*) |
+----------+
|        8 |
+----------+
1 row in set (0.00 sec)

mysql> select count(name) from exam_result;
-- 遇到null,不进行统计
+-------------+
| count(name) |
+-------------+
|           7 |
+-------------+

指定列进行去重

mysql>  update exam_result set math = 98 where name = '猪悟能';

mysql> select * from exam_result;
+------+--------+---------+------+---------+
| id   | name   | chinese | math | english |
+------+--------+---------+------+---------+
|    1 | 唐三藏 |    67.0 | 98.0 |    56.0 |
|    2 | 孙悟空 |    87.5 | 78.0 |    77.0 |
|    3 | 猪悟能 |    88.0 | 98.0 |    90.0 |
|    4 | 曹孟德 |    82.0 | 84.0 |    67.0 |
|    5 | 刘玄德 |    55.5 | 85.0 |    45.0 |
|    6 | 孙权   |    70.0 | 73.0 |    78.5 |
|    7 | 宋公明 |    75.0 | 65.0 |    30.0 |
| NULL | NULL   |    NULL | NULL |    NULL |
+------+--------+---------+------+---------+


mysql> select count(distinct math)from exam_result;
-- 统计数学成绩去重后的个数(null不算,重复的不算)
+----------------------+
| count(distinct math) |
+----------------------+
|                    6 |
+----------------------+
  • sum()求和

    把这一列的若干行,进行求和算数运算(只能针对数字类型使用 )

mysql> select sum(chinese) from exam_result;
-- 计算所有人语文成绩之和。(会自动排除null)
+--------------+
| sum(chinese) |
+--------------+
|        525.0 |
+--------------+

mysql> select sum(name) from exam_result;
-- 如果是字符串来参与运算,会进行警告
+-----------+
| sum(name) |
+-----------+
|         0 |
+-----------+
1 row in set, 7 warnings (0.01 sec)

mysql> show warnings;
-- mysql会尝试把这一列转换成double,如果可以转成double,就可以进行运算。如果没有转成就会报错。
+---------+------+--------------------------------------------+
| Level   | Code | Message                                    |
+---------+------+--------------------------------------------+
| Warning | 1292 | Truncated incorrect DOUBLE value: '唐三藏' |
| Warning | 1292 | Truncated incorrect DOUBLE value: '孙悟空' |
| Warning | 1292 | Truncated incorrect DOUBLE value: '猪悟能' |
| Warning | 1292 | Truncated incorrect DOUBLE value: '曹孟德' |
| Warning | 1292 | Truncated incorrect DOUBLE value: '刘玄德' |
| Warning | 1292 | Truncated incorrect DOUBLE value: '孙权'   |
| Warning | 1292 | Truncated incorrect DOUBLE value: '宋公明' |
+---------+------+--------------------------------------------+

-- sum(表达式)
mysql> select sum(chinese+math+english) from exam_result;
-- 1,先把对于的列相加,得到一个临时表
-- 2.把这个临时表的结果,进行行与行之间的运算
+---------------------------+
| sum(chinese+math+english) |
+---------------------------+
|                    1549.5 |
+---------------------------+
  • avg ()求平均值

    mysql> select avg(chinese) from exam_result;
    +--------------+
    | avg(chinese) |
    +--------------+
    |     75.00000 |
    +--------------+
    
    
  • min() max() 求最大最小值

mysql> select min(chinese) from exam_result;
+--------------+
| min(chinese) |
+--------------+
|         55.5 |
+--------------+
1 row in set (0.01 sec)

mysql> select max(chinese) from exam_result;
+--------------+
| max(chinese) |
+--------------+
|         88.0 |
+--------------+
1 row in set (0.00 sec)
2.group by 子句
  • 使用group by进行分组,再针对每个分组,分别进行聚合查询

  • 针对指定的列进行分组,把这一列中值相同的行,分到一组中,得到若干个组。对这些组分别使用聚合函数。

mysql> select * from emp;
+----+------+----------+--------+
| id | name | role     | salary |
+----+------+----------+--------+
|  1 | 张三 | 程序员   |  10000 |
|  2 | 李四 | 程序员   |  12000 |
|  3 | 王五 | 程序员   |  13000 |
|  4 | 赵六 | 产品经理 |   9000 |
|  5 | 李白 | 产品经理 |   9500 |
|  6 | 周八 | 老板     | 100000 |
+----+------+----------+--------+
6 rows in set (0.00 sec)

mysql> select avg(salary) from emp;
+-------------+
| avg(salary) |
+-------------+
|  25583.3333 |
+-------------+
1 row in set (0.00 sec)

mysql> select role,avg(salary) from emp group by role;
-- 1.先根据role进行分组
-- 2.再针对每组来求平均值
+----------+-------------+
| role     | avg(salary) |
+----------+-------------+
| 产品经理 |   9250.0000 |
| 程序员   |  11666.6667 |
| 老板     | 100000.0000 |
+----------+-------------+
  • 如果分组之后,不使用聚合函数。此时的结果就是查询出每一组中的某个代表数据。

搭配条件

要区分好是分组前的条件,还是分组后的条件。

mysql>  select role,avg(salary)from emp where name!='张三' group by role;
-- 查询每个岗位的平均工资,但是排除张三
+----------+-------------+
| role     | avg(salary) |
+----------+-------------+
| 产品经理 |   9250.0000 |
| 程序员   |  12500.0000 |
| 老板     | 100000.0000 |
+----------+-------------+
3 rows in set (0.01 sec)


3.having
  • 在对分组后的结果再次进行条件过滤时,不能使用where语句,而是需要使用having
  • having 一般写在 group by的后面
-- 查询每个岗位的平均工资,但是排除平均工资超过两万的结果

mysql>  select role,avg(salary)from emp group by role having avg(salary)<20000;
+----------+-------------+
| role     | avg(salary) |
+----------+-------------+
| 产品经理 |   9250.0000 |
| 程序员   |  11666.6667 |
+----------+-------------+
  • 在group by 中,可以一个sql同时完成这两类条件的筛选
-- 查询每个岗位的平均薪资,不算张三,并且保留 平均值<2万的结果 
mysql>  select role,avg(salary)  from emp where name !='张三' group by role having avg(salary)<20000;
+----------+-------------+
| role     | avg(salary) |
+----------+-------------+
| 产品经理 |   9250.0000 |
| 程序员   |  12500.0000 |
+----------+-------------+

2.联合查询

一次需要在多张表中进行查询。

联合查询/多表查询 :是对多张表的数据取笛卡尔积

笛卡尔积

在这里插入图片描述

  • 笛卡尔积是通过排列组合的方式,得到一个更大的表
  • 笛卡尔积的列数,是这两个表的列数相加。
  • 笛卡尔积的行数,是这两个表的行数相乘。

​ 笛卡尔积列举了所有可能的情况。其中,有些数据可能是非法的(无意义的数据)。在进行多表查询的时候,就需要把有意义的数据筛选出来,过滤掉无意义的数据。筛序的条件叫做连接条件。

mysql> create table classes(id int primary key auto_increment,name varchar(20), `desc` varchar(100));
Query OK, 0 rows affected (0.01 sec)

mysql> create table student(id int primary key auto_increment,sn varchar(20),name varchar(20), qq_mail varchar(20),classes_id int);
Query OK, 0 rows affected (0.00 sec)

mysql> create table course(id int primary key auto_increment,name varchar(20));
Query OK, 0 rows affected (0.01 sec)

mysql> create table score(score decimal(3,1),student_id int,course_id int);
Query OK, 0 rows affected (0.01 sec)

insert into classes(name, `desc`) values 
('计算机系2019级1班', '学习了计算机原理、C和Java语言、数据结构和算法'),
('中文系2019级3班','学习了中国传统文学'),
('自动化2019级5班','学习了机械自动化');
insert into student(sn, name, qq_mail, classes_id) values
('09982','黑旋风李逵','xuanfeng@qq.com',1),
('00835','菩提老祖',null,1),
('00391','白素贞',null,1),
('00031','许仙','xuxian@qq.com',1),
('00054','不想毕业',null,1),
('51234','好好说话','say@qq.com',2),
('83223','tellme',null,2),
('09527','老外学中文','foreigner@qq.com',2);
insert into course(name) values
('Java'),('中国传统文化'),('计算机原理'),('语文'),('高阶数学'),('英文');
insert into score(score, student_id, course_id) values
-- 黑旋风李逵
(70.5, 1, 1),(98.5, 1, 3),(33, 1, 5),(98, 1, 6),
-- 菩提老祖
(60, 2, 1),(59.5, 2, 5),
-- 白素贞
(33, 3, 1),(68, 3, 3),(99, 3, 5),
-- 许仙
(67, 4, 1),(23, 4, 3),(56, 4, 5),(72, 4, 6),
-- 不想毕业
(81, 5, 1),(37, 5, 5),
-- 好好说话
(56, 6, 2),(43, 6, 4),(79, 6, 6),
-- tellme
(80, 7, 2),(92, 7, 6);


mysql> show tables;
+-------------------+
| Tables_in_day5_14 |
+-------------------+
| classes           |
| course            |
| score             |
| student           |
+-------------------+
-- 学生表、班级表、课程表

-- 分数表(学生和课程之间的联系表)
-- 学生表
mysql> select * from student;
+----+-------+------------+------------------+------------+
| id | sn    | name       | qq_mail          | classes_id |
+----+-------+------------+------------------+------------+
|  1 | 09982 | 黑旋风李逵 | xuanfeng@qq.com  |          1 |
|  2 | 00835 | 菩提老祖   | NULL             |          1 |
|  3 | 00391 | 白素贞     | NULL             |          1 |
|  4 | 00031 | 许仙       | xuxian@qq.com    |          1 |
|  5 | 00054 | 不想毕业   | NULL             |          1 |
|  6 | 51234 | 好好说话   | say@qq.com       |          2 |
|  7 | 83223 | tellme     | NULL             |          2 |
|  8 | 09527 | 老外学中文 | foreigner@qq.com |          2 |
+----+-------+------------+------------------+------------+
-- 班级表
mysql> select * from classes;
+----+-------------------+-----------------------------------------------+
| id | name              | desc                                          |
+----+-------------------+-----------------------------------------------+
|  1 | 计算机系20191| 学习了计算机原理、C和Java语言、数据结构和算法 |
|  2 | 中文系20193| 学习了中国传统文学                            |
|  3 | 自动化20195| 学习了机械自动化                              |
+----+-------------------+-----------------------------------------------+

-- 课程表
mysql> select * from course;
+----+--------------+
| id | name         |
+----+--------------+
|  1 | Java         |
|  2 | 中国传统文化 |
|  3 | 计算机原理   |
|  4 | 语文         |
|  5 | 高阶数学     |
|  6 | 英文         |
+----+--------------+
-- 分数表
mysql> select * from score;
+-------+------------+-----------+
| score | student_id | course_id |
+-------+------------+-----------+
|  70.5 |          1 |         1 |
|  98.5 |          1 |         3 |
|  33.0 |          1 |         5 |
|  98.0 |          1 |         6 |
|  60.0 |          2 |         1 |
|  59.5 |          2 |         5 |
|  33.0 |          3 |         1 |
|  68.0 |          3 |         3 |
|  99.0 |          3 |         5 |
|  67.0 |          4 |         1 |
|  23.0 |          4 |         3 |
|  56.0 |          4 |         5 |
|  72.0 |          4 |         6 |
|  81.0 |          5 |         1 |
|  37.0 |          5 |         5 |
|  56.0 |          6 |         2 |
|  43.0 |          6 |         4 |
|  79.0 |          6 |         6 |
|  80.0 |          7 |         2 |
|  92.0 |          7 |         6 |
+-------+------------+-----------+
1.内连接
查询许仙同学的成绩

1.先把student和score两张表进行笛卡尔积

mysql>  select * from student,score;
+----+-------+------------+------------------+------------+-------+------------+-----------+
| id | sn    | name       | qq_mail          | classes_id | score | student_id | course_id |
+----+-------+------------+------------------+------------+-------+------------+-----------+
|  1 | 09982 | 黑旋风李逵 | xuanfeng@qq.com  |          1 |  70.5 |          1 |         1 |
|  2 | 00835 | 菩提老祖   | NULL             |          1 |  70.5 |          1 |         1 |
|  3 | 00391 | 白素贞     | NULL             |          1 |  70.5 |          1 |         1 |
|  4 | 00031 | 许仙       | xuxian@qq.com    |          1 |  70.5 |          1 |         1 |
-- --------     --------------------------------------- - - - - - - -  - -   - --- - - - -
|  6 | 51234 | 好好说话   | say@qq.com       |          2 |  92.0 |          7 |         6 |
|  7 | 83223 | tellme     | NULL             |          2 |  92.0 |          7 |         6 |
|  8 | 09527 | 老外学中文 | foreigner@qq.com |          2 |  92.0 |          7 |         6 |
+----+-------+------------+------------------+------------+-------+------------+-----------+
160 rows in set (0.01 sec)

-- 一共160行(20*8)5列(2+3),中间省略

2.加上连接条件,筛选出有效数据

学生id在两个表中同时出现。筛选条件为: 学生表的id = 分数表的student_id

 select * from student,score where id = student_id;
 -- 但是如果两个表的列名一样,则无法进行区分
 
  select * from student,score where student.id = score.student_id;
  -- 所以用表名.列名进行区分。
  +----+-------+------------+-----------------+------------+-------+------------+-----------+
| id | sn    | name       | qq_mail         | classes_id | score | student_id | course_id |
+----+-------+------------+-----------------+------------+-------+------------+-----------+
|  1 | 09982 | 黑旋风李逵 | xuanfeng@qq.com |          1 |  70.5 |          1 |         1 |
|  1 | 09982 | 黑旋风李逵 | xuanfeng@qq.com |          1 |  98.5 |          1 |         3 |
|  1 | 09982 | 黑旋风李逵 | xuanfeng@qq.com |          1 |  33.0 |          1 |         5 |
|  1 | 09982 | 黑旋风李逵 | xuanfeng@qq.com |          1 |  98.0 |          1 |         6 |
|  2 | 00835 | 菩提老祖   | NULL            |          1 |  60.0 |          2 |         1 |
|  2 | 00835 | 菩提老祖   | NULL            |          1 |  59.5 |          2 |         5 |
|  3 | 00391 | 白素贞     | NULL            |          1 |  33.0 |          3 |         1 |
|  3 | 00391 | 白素贞     | NULL            |          1 |  68.0 |          3 |         3 |
|  3 | 00391 | 白素贞     | NULL            |          1 |  99.0 |          3 |         5 |
|  4 | 00031 | 许仙       | xuxian@qq.com   |          1 |  67.0 |          4 |         1 |
|  4 | 00031 | 许仙       | xuxian@qq.com   |          1 |  23.0 |          4 |         3 |
|  4 | 00031 | 许仙       | xuxian@qq.com   |          1 |  56.0 |          4 |         5 |
|  4 | 00031 | 许仙       | xuxian@qq.com   |          1 |  72.0 |          4 |         6 |
|  5 | 00054 | 不想毕业   | NULL            |          1 |  81.0 |          5 |         1 |
|  5 | 00054 | 不想毕业   | NULL            |          1 |  37.0 |          5 |         5 |
|  6 | 51234 | 好好说话   | say@qq.com      |          2 |  56.0 |          6 |         2 |
|  6 | 51234 | 好好说话   | say@qq.com      |          2 |  43.0 |          6 |         4 |
|  6 | 51234 | 好好说话   | say@qq.com      |          2 |  79.0 |          6 |         6 |
|  7 | 83223 | tellme     | NULL            |          2 |  80.0 |          7 |         2 |
|  7 | 83223 | tellme     | NULL            |          2 |  92.0 |          7 |         6 |
+----+-------+------------+-----------------+------------+-------+------------+-----------+

3.结合需求,进一步添加条件,针对结果进行筛选。


mysql>  select * from student,score where student.id = score.student_id and student.name = '许仙';
+----+-------+------+---------------+------------+-------+------------+-----------+
| id | sn    | name | qq_mail       | classes_id | score | student_id | course_id |
+----+-------+------+---------------+------------+-------+------------+-----------+
|  4 | 00031 | 许仙 | xuxian@qq.com |          1 |  67.0 |          4 |         1 |
|  4 | 00031 | 许仙 | xuxian@qq.com |          1 |  23.0 |          4 |         3 |
|  4 | 00031 | 许仙 | xuxian@qq.com |          1 |  56.0 |          4 |         5 |
|  4 | 00031 | 许仙 | xuxian@qq.com |          1 |  72.0 |          4 |         6 |
+----+-------+------+---------------+------------+-------+------------+-----------+

4.针对查询到的列,进行精简。只保留需求。

 mysql>  select student.name,score.score from student,score where student.id = score.student_id and student.name = '许仙';
+------+-------+
| name | score |
+------+-------+
| 许仙 |  67.0 |
| 许仙 |  23.0 |
| 许仙 |  56.0 |
| 许仙 |  72.0 |
+------+-------+
查询所有同学的总成绩

​ 用聚合函数sum对多行数据进行加和,还需要按照同学来进行分组

1.先将学生表和分数表进行笛卡尔积

mysql> select * from student,score;

2.指定连接条件 student.id = score.student_id


mysql> select * from student,score where student.id = score.student_id;
+----+-------+------------+-----------------+------------+-------+------------+-----------+
| id | sn    | name       | qq_mail         | classes_id | score | student_id | course_id |
+----+-------+------------+-----------------+------------+-------+------------+-----------+
|  1 | 09982 | 黑旋风李逵 | xuanfeng@qq.com |          1 |  70.5 |          1 |         1 |
|  1 | 09982 | 黑旋风李逵 | xuanfeng@qq.com |          1 |  98.5 |          1 |         3 |
|  1 | 09982 | 黑旋风李逵 | xuanfeng@qq.com |          1 |  33.0 |          1 |         5 |
|  1 | 09982 | 黑旋风李逵 | xuanfeng@qq.com |          1 |  98.0 |          1 |         6 |
|  2 | 00835 | 菩提老祖   | NULL            |          1 |  60.0 |          2 |         1 |
|  2 | 00835 | 菩提老祖   | NULL            |          1 |  59.5 |          2 |         5 |
|  3 | 00391 | 白素贞     | NULL            |          1 |  33.0 |          3 |         1 |
|  3 | 00391 | 白素贞     | NULL            |          1 |  68.0 |          3 |         3 |
|  3 | 00391 | 白素贞     | NULL            |          1 |  99.0 |          3 |         5 |
|  4 | 00031 | 许仙       | xuxian@qq.com   |          1 |  67.0 |          4 |         1 |
|  4 | 00031 | 许仙       | xuxian@qq.com   |          1 |  23.0 |          4 |         3 |
|  4 | 00031 | 许仙       | xuxian@qq.com   |          1 |  56.0 |          4 |         5 |
|  4 | 00031 | 许仙       | xuxian@qq.com   |          1 |  72.0 |          4 |         6 |
|  5 | 00054 | 不想毕业   | NULL            |          1 |  81.0 |          5 |         1 |
|  5 | 00054 | 不想毕业   | NULL            |          1 |  37.0 |          5 |         5 |
|  6 | 51234 | 好好说话   | say@qq.com      |          2 |  56.0 |          6 |         2 |
|  6 | 51234 | 好好说话   | say@qq.com      |          2 |  43.0 |          6 |         4 |
|  6 | 51234 | 好好说话   | say@qq.com      |          2 |  79.0 |          6 |         6 |
|  7 | 83223 | tellme     | NULL            |          2 |  80.0 |          7 |         2 |
|  7 | 83223 | tellme     | NULL            |          2 |  92.0 |          7 |         6 |
+----+-------+------------+-----------------+------------+-------+------------+-----------+

3.先精简列


mysql> select student.name,score.score from student,score where student.id = score.student_id;
+------------+-------+
| name       | score |
+------------+-------+
| 黑旋风李逵 |  70.5 |
| 黑旋风李逵 |  98.5 |
| 黑旋风李逵 |  33.0 |
| 黑旋风李逵 |  98.0 |
| 菩提老祖   |  60.0 |
| 菩提老祖   |  59.5 |
| 白素贞     |  33.0 |
| 白素贞     |  68.0 |
| 白素贞     |  99.0 |
| 许仙       |  67.0 |
| 许仙       |  23.0 |
| 许仙       |  56.0 |
| 许仙       |  72.0 |
| 不想毕业   |  81.0 |
| 不想毕业   |  37.0 |
| 好好说话   |  56.0 |
| 好好说话   |  43.0 |
| 好好说话   |  79.0 |
| tellme     |  80.0 |
| tellme     |  92.0 |
+------------+-------+

4.对上述结果,进行group by聚合查询

mysql> select student.name,sum(score.score) from student,score where student.id = score.student_id group by student.name  ;
+------------+------------------+
| name       | sum(score.score) |
+------------+------------------+
| tellme     |            172.0 |
| 不想毕业   |            118.0 |
| 好好说话   |            178.0 |
| 白素贞     |            200.0 |
| 菩提老祖   |            119.5 |
| 许仙       |            218.0 |
| 黑旋风李逵 |            300.0 |
+------------+------------------+
查询所有同学的每门课程和分数:

1.学生表、课程表、分数表三张表进行笛卡尔积

mysql> select * from student,course,score;

2.指定连接条件筛选数据。三个表涉及到两个连接条件。

score.student_id = student,id

score.course_id = course.id

mysql> select * from student,course,score where student.id = score.student_id and score.course_id = course.id ;

3.精简列


mysql> select student.name,course.name,score.score from student,course,score where student.id = score.student_id and score.course_id = course.id ;
-- 进行取别名
mysql> select student.name as studentName,course.name as courseName ,score.score from student,course,score where student.id = score.student_id and score.course_id = course.id ;
+-------------+--------------+-------+
| studentName | courseName   | score |
2.外连接

左外连接 :左侧的表完全显示 (left join)

右外连接 :右侧的表完全显示 (right jion)

如果两个表中,里面的记录都是存在对应关系,内连接和外连接的结果就是一致的

如果存在不对于的记录,内连接和外连接就会出现差别。

mysql> insert into student2 values(1,'张三'),(2,'李四'),(3,'王五');
Query OK, 3 rows affected (0.01 sec)
Records: 3  Duplicates: 0  Warnings: 0

mysql> insert into score2 value(1,90),(2,80),(4,70);
Query OK, 3 rows affected (0.01 sec)

mysql> select * from student2;
+------+------+
| id   | name |
+------+------+
|    1 | 张三 |
|    2 | 李四 |
|    3 | 王五 |
+------+------+
3 rows in set (0.00 sec)

mysql> select * from score2;
+------+-------+
| id   | score |
+------+-------+
|    1 |    90 |
|    2 |    80 |
|    4 |    70 |
+------+-------+
1.内连接:
mysql>  select * from student2,score2 where student2.id = score2.id;
-- 内连接写法一
+------+------+------+-------+
| id   | name | id   | score |
+------+------+------+-------+
|    1 | 张三 |    1 |    90 |
|    2 | 李四 |    2 |    80 |
+------+------+------+-------+

mysql>  select * from student2 [inner] join score2 on student2.id = score2.id;
-- 内连接写法二
+------+------+------+-------+
| id   | name | id   | score |
+------+------+------+-------+
|    1 | 张三 |    1 |    90 |
|    2 | 李四 |    2 |    80 |
+------+------+------+-------+
2.左外连接
mysql>  select * from student2 left join score2 on student2.id = score2.id;
+------+------+------+-------+
| id   | name | id   | score |
+------+------+------+-------+
|    1 | 张三 |    1 |    90 |
|    2 | 李四 |    2 |    80 |
|    3 | 王五 | NULL |  NULL |
+------+------+------+-------+
  • 王五的数据只在左侧表(student2)存在
  • 以左侧表为基准,保证左侧表的每个记录都体现在结果中。如果在右侧表中不存在,就填成null
3.右外链接
mysql>  select * from student2 right join score2 on student2.id = score2.id;
+------+------+------+-------+
| id   | name | id   | score |
+------+------+------+-------+
|    1 | 张三 |    1 |    90 |
|    2 | 李四 |    2 |    80 |
| NULL | NULL |    4 |    70 |
+------+------+------+-------+
  • 以右侧表为基准,保证右侧表的每个数据,都会出现在最终结果里。如果左侧表中不存在,对于的列填null
3.自连接
  • 一张表,自己和自己进行笛卡尔积。

有的时候,需要进行与行之间的比较。而sql只能进行列和列之间的比较。通过自连接,把行关系转换成列关系

显示所有“计算机原理”成绩比“Java”成绩高的成绩信息

mysql> select * from score;
+-------+------------+-----------+
| score | student_id | course_id |
+-------+------------+-----------+
|  70.5 |          1 |         1 |
|  98.5 |          1 |         3 |
|  33.0 |          1 |         5 |
|  98.0 |          1 |         6 |
|  60.0 |          2 |         1 |
|  59.5 |          2 |         5 |
|  33.0 |          3 |         1 |
|  68.0 |          3 |         3 |
|  99.0 |          3 |         5 |
|  67.0 |          4 |         1 |
|  23.0 |          4 |         3 |
|  56.0 |          4 |         5 |
|  72.0 |          4 |         6 |
|  81.0 |          5 |         1 |
|  37.0 |          5 |         5 |
|  56.0 |          6 |         2 |
|  43.0 |          6 |         4 |
|  79.0 |          6 |         6 |
|  80.0 |          7 |         2 |
|  92.0 |          7 |         6 |
+-------+------------+-----------+
mysql> select * from course;
+----+--------------+
| id | name         |
+----+--------------+
|  1 | Java         |
|  2 | 中国传统文化 |
|  3 | 计算机原理   |
|  4 | 语文         |
|  5 | 高阶数学     |
|  6 | 英文         |
+----+--------------+
-- 看3比1高的成绩

要将行关系,转换成列关系,

 mysql> select * from score,score;
ERROR 1066 (42000): Not unique table/alias: 'score'
-- 不能直接用,需要设置别名
mysql> select * from score as s1,score as s2;
mysql> select * from score as s1,score as s2 where s1.student_id = s2.student_id and s1.course_id=3 and s2.course_id = 1;
+-------+------------+-----------+-------+------------+-----------+
| score | student_id | course_id | score | student_id | course_id |
+-------+------------+-----------+-------+------------+-----------+
|  98.5 |          1 |         3 |  70.5 |          1 |         1 |
|  68.0 |          3 |         3 |  33.0 |          3 |         1 |
|  23.0 |          4 |         3 |  67.0 |          4 |         1 |
+-------+------------+-----------+-------+------------+-----------+
3 rows in set (0.00 sec)

mysql> select * from score as s1,score as s2 where s1.student_id = s2.student_id and s1.course_id=3 and s2.course_id = 1 and s1.score>s2.score;
+-------+------------+-----------+-------+------------+-----------+
| score | student_id | course_id | score | student_id | course_id |
+-------+------------+-----------+-------+------------+-----------+
|  98.5 |          1 |         3 |  70.5 |          1 |         1 |
|  68.0 |          3 |         3 |  33.0 |          3 |         1 |
+-------+------------+-----------+-------+------------+-----------+
2 rows in set (0.00 sec)

mysql> select s1.student_id,s1.score,s2.score from score as s1,score as s2 where s1.student_id = s2.student_id and s1.course_id=3 and s2.course_id = 1 and s1.score>s2.score;
+------------+-------+-------+
| student_id | score | score |
+------------+-------+-------+
|          1 |  98.5 |  70.5 |
|          3 |  68.0 |  33.0 |
+------------+-------+-------+
4.子查询

也叫嵌套查询:嵌入到其他sql语句中select语句。(套娃)

单行子查询
  • 返回一行记录的子查询

查询与“不想毕业” 同学的同班同学:

mysql> select * from student;
+----+-------+------------+------------------+------------+
| id | sn    | name       | qq_mail          | classes_id |
+----+-------+------------+------------------+------------+
|  1 | 09982 | 黑旋风李逵 | xuanfeng@qq.com  |          1 |
|  2 | 00835 | 菩提老祖   | NULL             |          1 |
|  3 | 00391 | 白素贞     | NULL             |          1 |
|  4 | 00031 | 许仙       | xuxian@qq.com    |          1 |
|  5 | 00054 | 不想毕业   | NULL             |          1 |
|  6 | 51234 | 好好说话   | say@qq.com       |          2 |
|  7 | 83223 | tellme     | NULL             |          2 |
|  8 | 09527 | 老外学中文 | foreigner@qq.com |          2 |
+----+-------+------------+------------------+------------+
8 rows in set (0.01 sec)

mysql> select * from student where classes_id = (select classes_id from student where name='不想毕业');
-- 第二个select 返回的结果是必须是一行记录
+----+-------+------------+-----------------+------------+
| id | sn    | name       | qq_mail         | classes_id |
+----+-------+------------+-----------------+------------+
|  1 | 09982 | 黑旋风李逵 | xuanfeng@qq.com |          1 |
|  2 | 00835 | 菩提老祖   | NULL            |          1 |
|  3 | 00391 | 白素贞     | NULL            |          1 |
|  4 | 00031 | 许仙       | xuxian@qq.com   |          1 |
|  5 | 00054 | 不想毕业   | NULL            |          1 |
+----+-------+------------+-----------------+------------+
多行子查询
  • 返回多行记录的子查询
查询“语文”或“英文”课程的成绩信息

1.先通过课程的名字,找到课程的id

2.通过课程id在分数表中进行查询

in
mysql> select * from score where course_id in (select id from course where name = '语文' or name = '英文');
mysql> select score.student_id,score.course_id,score.score from score where score.course_id in (select id from course where name = '语文' or name = '英文');
+------------+-----------+-------+
| student_id | course_id | score |
+------------+-----------+-------+
|          1 |         6 |  98.0 |
|          4 |         6 |  72.0 |
|          6 |         4 |  43.0 |
|          6 |         6 |  79.0 |
|          7 |         6 |  92.0 |
+------------+-----------+-------+
5.合并查询
  • 把多个sql的结果集,合并到一起。
union
  • 前后查询的结果集,字段必须一致
  • 用于取两个不同表的结果集的并集。会自动去掉重复行。

查询id小于3,或者名字为“英文”的课程

mysql> select * from course where  id<3 or name = '英文';
-- or只能一个表
+----+--------------+
| id | name         |
+----+--------------+
|  1 | Java         |
|  2 | 中国传统文化 |
|  6 | 英文         |
+----+--------------+
mysql> select * from course where  id<3 union select * from course where name = '英文';
-- union 可以合并两个不同表的结果集
-- 两个表列的个数和类型必须一致。
+----+--------------+
| id | name         |
+----+--------------+
|  1 | Java         |
|  2 | 中国传统文化 |
|  6 | 英文         |
+----+--------------+
  • 如果不需要去重,使用union all

点击移步博客主页,欢迎光临~

偷cyk的图

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

CA、ukey、java对接登录

Ukey登录 随着互联网技术的发展&#xff0c;越来越多的应用需要用户进行登录&#xff0c;以验证其身份和权限。为了增强安全性&#xff0c;许多应用选择使用硬件设备来存储和管理用户的身份信息。Ukey&#xff08;也称为USB Key&#xff09;是一种常见的硬件设备&#xff0c;用…

【极简】docker常用操作

镜像images是静态的 容器container是动态的&#xff0c;是基于镜像的&#xff0c;类似于一个进程。 查看docker images&#xff1a; docker images 或者docker image ls 查看docker container情况&#xff1a;docker ps -a&#xff0c;-a意思是--all 运行一个container: doc…

高效水深度除六价铬工艺的技术研究与应用

关键词&#xff1a;六价铬&#xff1b;水处理&#xff1b;离子交换&#xff1b;环境保护&#xff1b;技术创新​ 随着工业化进程的加速&#xff0c;重金属污染尤其是六价铬的排放问题日益严重。六价铬是一种高度有害的污染物&#xff0c;广泛存在于电镀、染料制造、皮革加工等…

JUnit5测试用例

1.用Test注解表示为测试方法 2.使用DisplayName定义别名 3.使用Assertions类的断言方法 使用断言&#xff0c;可以判断方法的实际执行结果和预期结果是否一致 assertEqualsassertTureassertNotNullassertAllassertThrows 下图是预期与实际不同时报错图 4.使用BeforeEach注解&…

【原创】java+springboot+mysql企业邮件管理系统设计与实现

个人主页&#xff1a;程序猿小小杨 个人简介&#xff1a;从事开发多年&#xff0c;Java、Php、Python、前端开发均有涉猎 博客内容&#xff1a;Java项目实战、项目演示、技术分享 文末有作者名片&#xff0c;希望和大家一起共同进步&#xff0c;你只管努力&#xff0c;剩下的交…

uniapp微信小程序使用vscode代替HBuilderX开发uniapp微信小程序并且vscode改动代码微信开发者工具能实时更新

前言 最近公司开发新的小程序项目&#xff0c;经调研综合所有人员考虑&#xff0c;用uni-app Vue3tsvite技术栈开发&#xff1b;而官方推荐使用HBuilderX开发&#xff0c;而考虑到目前公司所有前端人员对VsCode更熟悉&#xff0c;故此总结了一下uniapp项目使用vscode代替HBuild…

vue3 + antd-vue@4 a-table单元格合并,rowSpan(行合并),colSpan(列合并)详解, 表头合并详解, 表头自定义详解

一、解释 1、rowSpan 1&#xff09;、行合并 2&#xff09;、当为0时&#xff1a;去掉边框 3&#xff09;、当为1时&#xff1a;不合并 4&#xff09;、大于1的x时&#xff1a;包含当前单元格行合并x个单元格 2、colSpan 1&#xff09;、列合并 2&#xff09;、当为0时&#xf…

C++ 将字符串解析为argc、argv

文章目录 前言一、如何实现&#xff1f;1、实现split2、split双引号3、奇数下标元素加入结果4、偶数下标元素split空格 二、完整代码三、使用示例1、解析命令行2、构造argc、argv 总结 前言 一般开启子进程的时候&#xff0c;需要传参数&#xff0c;通常直接传输命令行字符串&…

SQL使用Groupby分组后,选择每个分组某个值最大的那一行

思路是&#xff1a; 先定位分组后某个值最大的值是多少根据值去全表匹配&#xff0c;得到对应的行 比如有个表&#xff1a; SELECT * FROM my_table按照sku_id分组后&#xff0c;选择record_date最大的那一行的全部值&#xff0c;先分组&#xff1a; SELECT sku_id,max(rec…

党建管理系统源码 搭建智慧党建小程序+支持在线缴费、考试、学习 功能强大

随着信息技术的飞速发展&#xff0c;党建工作也迎来了数字化、智能化的新时代。为了提升党建工作的效率&#xff0c;优化党员参与体验&#xff0c;基于党建管理系统源码的智慧党建小程序非常好用。分享一款春哥智慧党建小程序源码&#xff0c;该小程序集成了在线缴费、考试、学…

什么是蜜罐,在当前网络安全形势下,蜜罐能提供哪些帮助

在当前的互联网时代&#xff0c;网络安全威胁日益严峻&#xff0c;攻击手段层出不穷。为了应对这些威胁&#xff0c;网络安全专家们不断探索新的防御手段&#xff0c;在过去的几年里&#xff0c;一种更加积极主动的网络安全方法正在兴起。蜜罐技术便是这样一种备受瞩目的主动防…

echers配置项:折线图,折现的颜色修改

如上图所示&#xff1a;红框内的折现颜色修改&#xff0c;并隐藏默认的点 series: [{data: [1, 230, 224, 218, 135, 147, 760,1500,1200,2500,2000],type: line,lineStyle: {color: #00DBFE // 折现颜色},symbol:none, // 不显示点smooth: true, // 折现角度&#xff1a;圆滑…

ARM架构安全特性之防御执行技术

安全之安全(security)博客目录导读 目录 1、侧信道攻击威胁 2、推测屏障Speculation Barriers 3、栈溢出攻击威胁 4、指针认证PAC 5、分支目标识别BTI 6、内存安全违规威胁 7、内存标记扩展MTE 8、加强数据保护 9、特权不可访问&#xff08;Privileged Access Never …

Unity Mirror 从入门到入神(一)

Mirror从入门到成神 文章目录 Mirror从入门到成神简介NetworkClientRegisterPrefabConnect (string address)Disconnect ()activeactiveHost NetworkServerSpawn 简介 Mirror是一个unity网络同步框架&#xff0c;基于MonoBehaviour生命周期的回调的基础上进行数值的同步&#…

算法day08

第一题 1. 两数之和 由上述题意所知&#xff0c;本题要采用二分法的解题思路&#xff0c;二分法主要是面向有序的数组且也满足二段性的数组&#xff0c;所谓二段性就是在一定的规则下能把该数组分成两个部分&#xff1b; 本题注意要点&#xff1a; 1、循环结束的条件&#xff…

MMDetection内三个实用工具详解:日志分析、结果分析、混淆矩阵

实用工具目录 一、日志分析使用方法实际案例 二、结果分析pkl结果文件生成使用方法实际案例 三、混淆矩阵使用方法实际案例遇到的UserWarning解决方案 MMDetection官方除了训练和测试脚本&#xff0c;他们还在 mmdetection/tools/ 目录下提供了许多有用的工具。本帖先为大家重点…

Blender雕刻建模_笔画,镜像,动态拓扑

笔画 笔画选项&#xff0c;一般是对刷子&#xff08;自由线&#xff09;工具设置 描边方法如下&#xff1a;标红的为常用 -间隔&#xff1a;按一定间隔应用笔画的结果 例如&#xff1a;笔刷半径50&#xff0c;笔画间隔100%&#xff08;笔刷直径的百分比&#xff09;&#x…

聚苯并咪唑(PBI)为超高性能工程塑料 未来应用前景较好

聚苯并咪唑&#xff08;PBI&#xff09;为超高性能工程塑料 未来应用前景较好 聚苯并咪唑&#xff08;简称PBI&#xff09;&#xff0c;是一类以苯并咪唑基团作为结构重复单元的杂环聚合物。聚苯并咪唑不溶于水&#xff0c;溶于强极性溶剂&#xff0c;具有耐高温、耐腐蚀、抗辐…

Java小游戏之汤姆猫

背景&#xff1a; 博主写过羊了个羊小游戏&#xff0c;客户觉得羊了个羊同学写过了&#xff0c;想换一个&#xff0c;于是笔者想到了汤姆猫。就是那个以前在苹果手机上的猫。 过程&#xff1a; 初始会有一个猫的图片展示&#xff0c;然后你点击按钮&#xff0c;猫会有不同动作…

Python筑基之旅-溯源及发展

目录 一、Python的起源 二、Python的版本更替及变化 三、Python的优缺点 四、Python的发展方向 五、Python之禅 六、推荐专栏/主页&#xff1a; 1、Python函数之旅&#xff1a;Functions 2、Python算法之旅&#xff1a;Algorithms 3、个人主页&#xff1a;https://mye…