数据库--数据库约束/聚合查询/分组查询/联合查询

news2024/12/23 13:59:52

       前言 

        逆水行舟,不进则退!!!     


目录

       数据库约束       

       聚合查询

       分组查询 

       联合查询 

       联合查询---内连接与外连接

       补充

       联合查询用到的代码


       数据库约束       

not null 约束:在创建表的时候,可以指定列插入的值不允许为null ;

语法:例:create table student (id int not null, name varchar(20) not null);

   


unique 约束:插入或修改 数据的时候,会先查询要 插入或修改 的数据是否已经存在,如果不存在,则可以 插入或修改;如果存在,则插入或修改失败;

语法:例:create table student (id int unique, name varchar(20));


default 约束:设置默认值,默认值是insert指定列插入的时候,其他未被指定的列就是按照默认值来填充的。

  语法:例:create table student (id int, name varchar(20) default '无名氏');

        


primary key 约束:设置主键值作为约束,在mysql中,要求一个表中,只能有一个主键。在创建主键的时候,可以使用一个列作为主键,也可以使用多个列作为主键(复合主键)。

        数据库中的主键是一种用于唯一标识表中每一行数据的字段或一组字段。主键的作用是确保表中每一行数据都有一个唯一的标识符,以便于在表中进行数据的查找、更新和删除等操作。主键还可以用于建立表之间的关系,例如在关系型数据库中,可以通过主键和外键来建立表与表之间的关联关系。

       主键所在的列不能为null,不能有重复,相当于同时加上了not null 约束 和 unique 约束。

语法:例:create table student (id int primary key, name varchar(20));

自增主键:  比普通主键多了一个要求,要求指定列必须是整数。

语法:create table student (id int primary key auto_increment, name varchar(20));

                

                        如果插入数据的时候,不指定主键,数据表会根据主键的值进行自动填充。但是需要注意一点,自增主键会根据主键的最大值进行自增填充。


foreign key 外键约束:用于在两个表之间建立链接。其中一个表的一个字段被另一个表中对应的字段所约束。被约束的表称为从表(子表),另一个表称为主表(父表)。外键约束可以确保数据的完整性和一致性,防止出现不一致的数据。

建立约束:先创建从表,然后再创建主表时,在字段后加上 foreign key (主表中列名) references 从表名(从表中要关联的列名) ;

验证约束:

约束是相互的。主表对从表有约束,同样的,从表对主表也有约束。


       聚合查询

        查询过程中,把表的行和行之间进行一定的运算。这个过程是依赖于一些聚合函数,也就是SQL提供的库函数

函数说明
COUNT([DISTINCT] expr)返回查询到的数据的 数量
SUM([DISTINCT] expr)返回查询到的数据的 总和,不是数字没有意义
AVG([DISTINCT] expr)返回查询到的数据的 平均值,不是数字没有意义
MAX([DISTINCT] expr)返回查询到的数据的 最大值,不是数字没有意义
MIN([DISTINCT] expr)返回查询到的数据的 最小值,不是数字没有意义

现有如下数据:我们将对这些数据进行演示。

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 |
|    8 | 如来佛祖     |    NULL | NULL |    NULL |
+------+--------------+---------+------+---------+
8 rows in set (0.00 sec)

count:返回查询到的数据的 数量

语法:select count(列名) from 表名

 全列查询:select count(*) from exam_result;

select count(*) from exam_result;
+----------+
| count(*) |
+----------+
|        8 |
+----------+
1 row in set (0.00 sec)

 单列查询:select count(列名) from exam_result;

select count(name) from exam_result;
+-------------+
| count(name) |
+-------------+
|           8 |
+-------------+
1 row in set (0.00 sec)
select count(chinese) from exam_result;
+----------------+
| count(chinese) |
+----------------+
|              7 |
+----------------+
1 row in set (0.00 sec)

        从上面代码,我们发现,在对某一列进行 count 查询时,如果某行的值为NULL,则该行不计入总个数中。

        注:count等聚合函数 与 () 中间不能有空格。 

sum:返回查询到的数据的 总和,不是数字没有意义

语法:select sum(列名) from exam_result;

select sum(chinese) from exam_result;
+--------------+
| sum(chinese) |
+--------------+
|        525.0 |
+--------------+
1 row in set (0.03 sec)

        在学sql的四则表达式时,我们说过,如果表达式中含有null,则表达式的结果为null;但若是聚合函数碰到了NULL值,则会直接跳过。

        当使用sum对字符串进行操作时,会有什么结果?

select sum(name) from exam_result;
+-----------+
| sum(name) |
+-----------+
|         0 |
+-----------+
1 row in set, 8 warnings (0.00 sec)
//可以看到,这里报了8个warning


show warnings;
+---------+------+--------------------------------------------------+
| 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: '宋公明'       |
| Warning | 1292 | Truncated incorrect DOUBLE value: '如来佛祖'     |
+---------+------+--------------------------------------------------+
8 rows in set (0.00 sec)

        其实不只是sum,其他只针对数字的聚合函数在对字符串进行操作的时候也都会报警告。

avg:返回查询到的数据的 平均值,不是数字没有意义

语法:select avg(列名) from exam_result;

select avg(chinese) from exam_result;
+--------------+
| avg(chinese) |
+--------------+
|     75.00000 |
+--------------+
1 row in set (0.03 sec)

        聚合函数还能搭配表达式使用。如求总分的平均分。

select avg(chinese + math + english) as avg_total from exam_result;
+-----------+
| avg_total |
+-----------+
| 221.42857 |
+-----------+
1 row in set (0.00 sec)

max:返回查询到的数据的 最大值,不是数字没有意义

min:返回查询到的数据的 最小值,不是数字没有意义

select max(chinese), min(chinese) from exam_result;
+--------------+--------------+
| max(chinese) | min(chinese) |
+--------------+--------------+
|         88.0 |         55.5 |
+--------------+--------------+
1 row in set (0.00 sec)


       分组查询 

        关键字 :group by

        分组查询常常和聚合查询搭配进行查询。

现有如下数据:

select * from emp;
+------+--------------+-----------+--------+
| id   | name         | role      | salary |
+------+--------------+-----------+--------+
|    1 | 孙悟空       | 讲师      |  10000 |
|    2 | 猪悟能       | 讲师      |  11000 |
|    3 | 沙悟净       | 讲师      |  12000 |
|    4 | 刘玄德       | 学管师    |  10000 |
|    5 | 曹孟德       | 学管师    |   9000 |
|    6 | 如来佛祖     | 老板      | 100000 |
|    7 | 太上老君     | 老板      | 120000 |
+------+--------------+-----------+--------+
7 rows in set (0.00 sec)

针对岗位进行分组查询平均薪资,执行结果如下:

select role, avg(salary) from emp group by role;
+-----------+-------------+
| role      | avg(salary) |
+-----------+-------------+
| 学管师    |   9500.0000 |
| 老板      | 110000.0000 |
| 讲师      |  11000.0000 |
+-----------+-------------+
3 rows in set (0.00 sec)

        查询的时候,这里的列,不能瞎写。select 指定的列,要么是带有聚合函数的列,要么就是group by 指定的列,不能指定一个非聚合非 group by 的列,否则无意义。举个例子:针对岗位查看员工姓名。查询结果如下:   这里的 name 列就是非聚合非 group by 的列。

select role, name from emp group by role;
+-----------+--------------+
| role      | name         |
+-----------+--------------+
| 学管师    | 刘玄德       |
| 老板      | 如来佛祖     |
| 讲师      | 孙悟空       |
+-----------+--------------+
3 rows in set (0.00 sec)

        还有更复杂的查询,如在分组的时候,可以指定条件筛选。这个时候就要搞清楚,筛选条件是在分组前,还是在分组后。

分组前筛选,使用where条件

例:求每个岗位的平均薪资,但是刨除 孙悟空 同学。

        这里的执行逻辑就是先将 孙悟空 同学除外,然后再进行分组,再求平均薪资。

select role, avg(salary) from emp where name != '孙悟空' group by role;
+-----------+-------------+
| role      | avg(salary) |
+-----------+-------------+
| 学管师    |   9500.0000 |
| 老板      | 110000.0000 |
| 讲师      |  11500.0000 |
+-----------+-------------+
3 rows in set (0.01 sec)

分组后筛选,使用having条件

例:求每个岗位的平均薪资,但是刨除 老板 这个岗位。

        这里的执行逻辑就是先分组,然后刨除 老板 这个岗位,再求平均薪资。

select role, avg(salary) from emp group by role having role != '老板';
+-----------+-------------+
| role      | avg(salary) |
+-----------+-------------+
| 学管师    |   9500.0000 |
| 讲师      |  11000.0000 |
+-----------+-------------+
2 rows in set (0.00 sec)

分组前后都筛选,同时使用where、having条件

例:先刨除 孙悟空 同学,然后求每个岗位的平均薪资,并且刨除 老板 这个岗位。

select role, avg(salary) from emp where name != '孙悟空' group by role having role != '老板';
+-----------+-------------+
| role      | avg(salary) |
+-----------+-------------+
| 学管师    |   9500.0000 |
| 讲师      |  11500.0000 |
+-----------+-------------+
2 rows in set (0.00 sec)

       联合查询 

        联合查询 又叫 多表查询。

        现有如下数据:    

select * from classes;
+----+-------------------------+-------------------------------------------------------------------+
| id | name                    | desc                                                              |
+----+-------------------------+-------------------------------------------------------------------+
|  1 | 计算机系2019级1班       | 学习了计算机原理、C和Java语言、数据结构和算法                     |
|  2 | 中文系2019级3班         | 学习了中国传统文学                                                |
|  3 | 自动化2019级5班         | 学习了机械自动化                                                  |
+----+-------------------------+-------------------------------------------------------------------+
3 rows in set (0.00 sec)





select * from course;
+----+--------------------+
| id | name               |
+----+--------------------+
|  1 | Java               |
|  2 | 中国传统文化       |
|  3 | 计算机原理         |
|  4 | 语文               |
|  5 | 高阶数学           |
|  6 | 英文               |
+----+--------------------+
6 rows in set (0.00 sec)








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.00 sec)





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 |
+-------+------------+-----------+
20 rows in set (0.00 sec)



       要进行联合查询,首先我们要先知道一个概念:笛卡尔积。 在SQL中呢,笛卡尔积是一种表与表之间的连接方式。两张表进行连接后,会对两张表中的每一行进行行组合。简单的说就是A表中的每一行都要与B表中的所有行进行一次组合。最后得到的组合表的行数是两张表的行之积,列数是两张表的列之和。这样呢就会导致很多的无效数据,所以我们需要对组合表进行一定的条件筛选。

例如:查询许仙同学的各科成绩
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 rows in set (0.01 sec)



//这里再显示一下各科的名称
select * from student, course, score where student.id = score.student_id and score.course_id = course.id and student.name = '许仙';
+----+-------+--------+---------------+------------+----+-----------------+-------+------------+-----------+
| id | sn    | name   | qq_mail       | classes_id | id | name            | score | student_id | course_id |
+----+-------+--------+---------------+------------+----+-----------------+-------+------------+-----------+
|  4 | 00031 | 许仙   | xuxian@qq.com |          1 |  1 | Java            |  67.0 |          4 |         1 |
|  4 | 00031 | 许仙   | xuxian@qq.com |          1 |  3 | 计算机原理       |  23.0 |          4 |         3 |
|  4 | 00031 | 许仙   | xuxian@qq.com |          1 |  5 | 高阶数学         |  56.0 |          4 |         5 |
|  4 | 00031 | 许仙   | xuxian@qq.com |          1 |  6 | 英文             |  72.0 |          4 |         6 |
+----+-------+--------+---------------+------------+----+-----------------+-------+------------+-----------+
4 rows in set (0.00 sec)



//然后再去除其他无关信息
select student.name, score.score, course.name from student, course, score where student.id = score.student_id and score.course_id = course.id and student.name = '许仙';
+--------+-------+-----------------+
| name   | score | name            |
+--------+-------+-----------------+
| 许仙   |  67.0 | Java            |
| 许仙   |  23.0 | 计算机原理      |
| 许仙   |  56.0 | 高阶数学        |
| 许仙   |  72.0 | 英文            |
+--------+-------+-----------------+
4 rows in set (0.00 sec)

mysql>

多表查询一般实现步骤:

1,分析清楚需求中,涉及到的信息都在那些表里;

2,针对这多个表进行笛卡尔积;

3,筛选出其中的有效数据;(演示代码中用学生id和课程id作为关联条件)

4,结合需求中的条件,进一步加强条件;

5,针对列进行精简。

在上述例子中,还有另一查询方式:通过 join on 来进行查询。这种查询方式与前一种查询方式有些不同:首先在表明之间不再用逗号隔开了,而是用 join 来隔开;然后,查询条件用 on 来代替 where。 这两种查询方式在效果上是相同的。


//与另一种查询方式相比,就是做了个替换。
select student.name, score.score, course.name from student join course join score where student.id = score.student_id and score.course_id = course.id and student.name = '许仙';
+--------+-------+-----------------+
| name   | score | name            |
+--------+-------+-----------------+
| 许仙   |  67.0 | Java            |
| 许仙   |  23.0 | 计算机原理      |
| 许仙   |  56.0 | 高阶数学        |
| 许仙   |  72.0 | 英文            |
+--------+-------+-----------------+
4 rows in set (0.00 sec)
例:查询所有同学的总成绩,以及同学的个人信息。
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 |
+----+-------+-----------------+-----------------+------------+-------+------------+-----------+
20 rows in set (0.00 sec)


//此时如何对每个学生的成绩进行求和呢?

//我们考虑分组,通过分组来对每个同学的成绩进行求和。
select * from student, score where student.id = score.student_id group by student.id;
+----+-------+-----------------+-----------------+------------+-------+------------+-----------+
| 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 |  60.0 |          2 |         1 |
|  3 | 00391 | 白素贞          | NULL            |          1 |  33.0 |          3 |         1 |
|  4 | 00031 | 许仙            | xuxian@qq.com   |          1 |  67.0 |          4 |         1 |
|  5 | 00054 | 不想毕业        | NULL            |          1 |  81.0 |          5 |         1 |
|  6 | 51234 | 好好说话        | say@qq.com      |          2 |  56.0 |          6 |         2 |
|  7 | 83223 | tellme          | NULL            |          2 |  80.0 |          7 |         2 |
+----+-------+-----------------+-----------------+------------+-------+------------+-----------+
7 rows in set (0.01 sec)

//分组后, 每个同学一条记录,但是呢,成绩并不是总分。

//要计算总分,要通过行之间的运算,这样就要用到聚合函数了
select student.name, sum(score.score) from student, score where student.id = score.student_id group by student.id;
+-----------------+------------------+
| name            | sum(score.score) |
+-----------------+------------------+
| 黑旋风李逵      |            300.0 |
| 菩提老祖        |            119.5 |
| 白素贞          |            200.0 |
| 许仙            |            218.0 |
| 不想毕业        |            118.0 |
| 好好说话        |            178.0 |
| tellme          |            172.0 |
+-----------------+------------------+
7 rows in set (0.01 sec)



       联合查询---内连接与外连接

        现有如下数据:

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




select * from score;
+------------+-------+
| student_id | score |
+------------+-------+
|          1 |    80 |
|          2 |    75 |
|          4 |    89 |
+------------+-------+
3 rows in set (0.00 sec)
内连接:在内连接中,只有当两个表中都存在与连接标准相匹配的数据时,才会保留这些数据。包括重复数据。
select * from student join score on student.id = score.student_id;
+------+--------+------------+-------+
| id   | name   | student_id | score |
+------+--------+------------+-------+
|    1 | 张三   |          1 |    80 |
|    2 | 李四   |          2 |    75 |
+------+--------+------------+-------+
2 rows in set (0.00 sec)

//这里再演示一下 内连接保留重复数据

//先在 student 表中插入一条相同的数据
insert into student values (2, '李四');
Query OK, 1 row affected (0.01 sec)



//查看此时的 student 表
select * from student;
+------+--------+
| id   | name   |
+------+--------+
|    1 | 张三   |
|    2 | 李四   |
|    3 | 王五   |
|    2 | 李四   |
+------+--------+
4 rows in set (0.00 sec)


//进行内连接查询

select * from student join score on student.id = score.student_id;
+------+--------+------------+-------+
| id   | name   | student_id | score |
+------+--------+------------+-------+
|    1 | 张三   |          1 |    80 |
|    2 | 李四   |          2 |    75 |
|    2 | 李四   |          2 |    75 |
+------+--------+------------+-------+
3 rows in set (0.00 sec)

多表内连接:语法:select * from 表1 join 表2 on 条件1 join 表3 on 条件2 ;
select * from student join score on student.id = score.student_id join course on student.id = course.student_id;
+------+--------+------------+-------+------------+--------+
| id   | name   | student_id | score | student_id | name   |
+------+--------+------------+-------+------------+--------+
|    1 | 张三   |          1 |    80 |          1 | 语文   |
+------+--------+------------+-------+------------+--------+
1 row in set (0.00 sec)

 

外连接:包括左外连接,右外连接。
左外连接:在 join 前加 left ,保留左表的全部数据;
select * from student left join score on student.id = score.student_id;
+------+--------+------------+-------+
| id   | name   | student_id | score |
+------+--------+------------+-------+
|    1 | 张三   |          1 |    80 |
|    2 | 李四   |          2 |    75 |
|    2 | 李四   |          2 |    75 |
|    3 | 王五   |       NULL |  NULL |
+------+--------+------------+-------+
4 rows in set (0.00 sec)
右外连接:在 join 前加 right ,保留右表的全部数据;
select * from student right join score on student.id = score.student_id;
+------+--------+------------+-------+
| id   | name   | student_id | score |
+------+--------+------------+-------+
|    1 | 张三   |          1 |    80 |
|    2 | 李四   |          2 |    75 |
|    2 | 李四   |          2 |    75 |
| NULL | NULL   |          4 |    89 |
+------+--------+------------+-------+
4 rows in set (0.00 sec)

       补充

自连接:  将行转成列   当需要比较行之间的关系时,可以考虑自连接,但是代价是相当的大,产生的数据中,绝大多数是无效数据

自连接语法: select * from 表1 as 别名1 join 表1 as 别名2 on 条件;

子查询:  将多个联合查询合并成一个查询,将查询中的一个值用另外一个查询语句来代替。(查询代价也是很大,基本不用)

        


       联合查询用到的代码
create table classes(id int primary key auto_increment, name varchar(20), `desc` varchar(100));


create table student (id int primary key auto_increment, sn varchar(20), name varchar(20),qq_mail varchar(20),classes_id int);


create table course(id int primary key auto_increment, name varchar(20));


create table score(score decimal(3,1), student_id int, course_id int);


mysql> insert into classes(name, `desc`) values
    -> ('计算机系2019级1班', '学习了计算机原理、C和Java语言、数据结构和算法'),
    -> ('中文系2019级3班','学习了中国传统文学'),
    -> ('自动化2019级5班','学习了机械自动化');


mysql> 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);


mysql> insert into course(name) values
    -> ('Java'),('中国传统文化'),('计算机原理'),('语文'),('高阶数学'),('英文');


mysql> 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);


        我是专注学习的章鱼哥~

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【实验记录】为了混毕业·读读论文叭

PR曲线 1. Robust_Place_Recognition_using_an_Imaging_Lidar 在第三节方法中,提到了一些列处理步骤,分析来与vins相似,在vins中是关键帧检索、特征提取、DBoW查询、描述子匹配、PnP RANSAC求解。 第四节的实验部分,没有绘制pr…

MyBatis 详解

目录 1.MyBatis 框架的搭建 1.1 创建数据库和表 1.2 添加 MyBatis 依赖 1.3 设置 MyBatis 配置 1.3.1 设置数据库的连接信息 1.3.2 设置 XML 保存路径和命名格式 1.4 根据 MyBatis 写法完成数据库得操作 1.4.1 定义接口 1.4.2 使用 XML 实现接口 2.MyBatis查询操作 …

手记系列之七 ----- 分享Linux使用经验

前言 本篇文章主要介绍的关于本人在使用Linux记录笔记的一些使用方法和经验,温馨提示,本文有点长,约1.7w字,几十张图片,建议收藏查看。 一、Linux基础使用 1,服务器查看及时日志 tail -500f catalina.out …

npm的使用

package.json 快速生成package.json npm init -y “version”: “~1.1.0” 格式为:「主版本号. 次版本号. 修订号」。 修改主版本号是做了大的功能性的改动 修改次版本号是新增了新功能 修改修订号就是修复了一些bug dependencies "dependencies": {&…

计算机组成与结构-计算机体系结构

计算机体系结构 指令系统 Flynn分类法 SISD(单指令流单数据流) 结构 控制部分:一个处理器:一个主存模块:一个 代表 单处理器系统 SIMD(单指令流多数据流) 结构 控制部分:一个处理…

2022年09月 Python(三级)真题解析#中国电子学会#全国青少年软件编程等级考试

Python等级考试(1~6级)全部真题・点这里 一、单选题(共25题,每题2分,共50分) 第1题 十六进制数100,对应的十进制数为 ?( ) A: 128 B: 256 C: 28 D: 56 答…

基于Qt命令行处理XML文件读写

Qt源码在后面,文本介绍Qt国际化语言和XML # XML基础(一) ## 1、概述 ### 1.1 定义(xml是个啥玩意儿?) XML(extensible Markup Language)俗称差妹儿,专业称之为:可拓展标记语言。 (1)何为标记,指的是一种标记语言,或者标签语言,即用一系列的标签来对数据进行…

Leetcode—421.数组中两个数的最大异或值【中等】明天写一下字典树做法!!!

2023每日刷题&#xff08;十九&#xff09; Leetcode—421.数组中两个数的最大异或值 算法思想 参考自灵茶山艾府 实现代码 class Solution { public:int findMaximumXOR(vector<int>& nums) {int maxValue *max_element(nums.begin(), nums.end());int highId…

STM32笔记-AD模数转换

目录 一、ADC介绍 二、ADC主要特征 三、ADC框图 1. ​​​​ 外部触发转换 ​ 2. 转换模式 3. 输入通道 4. 逻辑框图 四、校准 五、数据对齐 六、AD转换步骤 七、AD_Init(单通道AD转换)初始化函数配置 一、ADC介绍 1. 12位ADC是一种逐次逼近型模拟数字转换器。它有多达…

扣人心弦玄幻小说,故事爽度堪比热门IP,堪称史诗级作品

《万古不死&#xff0c;葬天&#xff0c;葬地&#xff0c;葬众生》 这本书是我看过最符合我心意的长生文。它始终在刻画一个长生者的经历&#xff0c;并且每一次的离别和悲伤都恰到好处。主角不是直接睡到无敌然后出去浪&#xff0c;而是不断学习&#xff0c;智商在线。坑杀雷族…

垃圾回收系统小程序定制开发搭建攻略

在这个数字化快速发展的时代&#xff0c;垃圾回收系统的推广对于环境保护和可持续发展具有重要意义。为了更好地服务于垃圾回收行业&#xff0c;本文将分享如何使用第三方制作平台乔拓云网&#xff0c;定制开发搭建垃圾回收系统小程序。 首先&#xff0c;使用乔拓云网账号登录平…

用户界面执行器设计场景-PR性能测试工具/压力测试工具

要使用 PerformanceRunner性能测试工具/压力测试工具测试您的系统&#xff0c;必须创建负载测试场景。场景定义每次测试期间发生的事件。场景定义并控制要模拟的用户数、这些用户执行的操作以及用于运行模拟场景的计算机。执行器负责设计场景、运行场景、控制场景、各种波形图生…

【广义表,树,满二叉树,完全二叉树,二叉树的存储结构】

文章目录 广义表树树的基本术语线性结构和树结构的比较二叉树的定义案例二叉树的性质和存储结构两种特殊形式下的二叉树满二叉树完全二叉树完全二叉树的性质 二叉树的存储结构二叉树的顺序存储结构二叉树的链式存储结构三叉链表 广义表 广义表&#xff08;又称Lists&#xff0…

建筑能源管理(8)——合同能源管理

1、简介 合同能源管理是20世纪70年代中期在发达国家逐步发展起来的一种节能服务机制在国外简称EPC(Energy Performance Contracting)&#xff0c;在国内广泛地被称为EMC (Energy Management Contracting)&#xff0c;它由专门的节能服务公司(Energy Service Company,ESCO)在为…

【KVM】软件虚拟化和硬件虚拟化类型

前言 大家好&#xff0c;我是秋意零。 今天介绍的内容是虚拟化技术以及软件虚拟化和硬件虚拟化。 &#x1f47f; 简介 &#x1f3e0; 个人主页&#xff1a; 秋意零&#x1f525; 账号&#xff1a;全平台同名&#xff0c; 秋意零 账号创作者、 云社区 创建者&#x1f9d1; 个…

Windows搭建Web站点:免费内网穿透发布至公网

目录 什么是cpolar&#xff1f; 概述 1. 注册并安装cpolar内网穿透 2. 搭建一个静态Web站点 2.1 下载演示站点 2.2 本地运行演示站点 2.3 本地浏览测试站点是否正常 3. 本地站点发布公网可访问 3.1 登录cpolar web ui管理界面 3.2 启动website隧道 3.3 获取公网URL地…

【数据结构】单链表详解(超详细)

单链表是我们学习数据结构时必不可少的部分&#xff0c;但也由于指针的参与变得更加复杂&#xff0c;这篇文章学习完之后可以更好地理解与掌握链表结构 注意&#xff1a; 数据结构中&#xff0c;不在乎菜单的创建&#xff0c;注重的是功能的实现&#xff1b;菜单的创建会影响我…

什么是协议栈? 用户态协议栈设计(udp协议栈)

什么是协议栈呢&#xff1f; &#xff08;协议栈&#xff08;Protocol Stack&#xff09;是计算机网络和通信系统中的一个重要概念&#xff0c;它指的是一组协议层的层次结构&#xff0c;这些协议层一起协同工作&#xff0c;以便在不同计算机或设备之间实现数据通信和交换。每…

开源 Wiki 软件 wiki.js

wiki.js简介 最强大、 可扩展的开源Wiki 软件。使用 Wiki.js 美观直观的界面让编写文档成为一种乐趣&#xff01;根据 AGPL-v3 许可证发布。 官方网站&#xff1a;https://js.wiki/ 项目地址&#xff1a;https://github.com/requarks/wiki 主要特性&#xff1a; 随处安装&a…

【从零开始学习Redis | 第四篇】基于延时双删对Cache Aside的优化

前言&#xff1a; 在如今的单体项目中&#xff0c;为了减轻大量相同请求对数据库的压力&#xff0c;我们采取了缓存中间件Redis。核心思想为&#xff1a;把数据写入到redis中&#xff0c;在查询的时候&#xff0c;就可以直接从Redis中拿取数据&#xff0c;这样我们原本对数据库…