子查询时将一个查询语句嵌套到另一个查询语句中。内层查询语句的查询结果,可以为外层查询语句提供查询条件。因为在特定情况下,一个查询语句的条件需要另一个查询语句来获取。通过子查询,可以实现多表之间的查询。子查询中可能包括in、not in、any、all、exists和not exists等关键字。子查询中还可能包含比较运算符,如:”=”、”!=”、”>”、”
1. 带in关键字的子查询
一个查询语句的条件可能落在另一个select语句的查询结果中。 这可以通过in关键字来判断。
我们查询employee表中的记录。这些记录的d_id字段的值必须在department表中出现过。在执行语句之前,先查看一下employee表department表的情况。
![a236754e711299cb750168eada40ab00.png](https://img-blog.csdnimg.cn/img_convert/a236754e711299cb750168eada40ab00.png)
![00cb61e9ee30dcc66d61dc66c5a119c1.png](https://img-blog.csdnimg.cn/img_convert/00cb61e9ee30dcc66d61dc66c5a119c1.png)
select * from employee where d_id in (select d_id from department);
![2f329c8875fa7d95ac1e78b6b20740ae.png](https://img-blog.csdnimg.cn/img_convert/2f329c8875fa7d95ac1e78b6b20740ae.png)
使用not in关键字查看d_id字段的值没在department表中的记录
select * from employee where d_id not in(select d_id from department);
![ed38e3b492003f24b8c72207068e8a0f.png](https://img-blog.csdnimg.cn/img_convert/ed38e3b492003f24b8c72207068e8a0f.png)
2. 带比较运算符的子查询
子查询可以使用比较运算符。这些比较运算符包括=、!=、>、>=、等。其中<>与=是等价的。比较运算符在子查询时使用的非常广泛。
下面从computer_stu表中查询获得一等奖学金的学生的学号、姓名和分数。各等级的奖学金的最低分存储在scholarship表中。
先查看一下computer_stu表和scholarship表
computer_stu表
![19dd9f355b9b8dc325ef18db73615e36.png](https://img-blog.csdnimg.cn/img_convert/19dd9f355b9b8dc325ef18db73615e36.png)
scholarship表
![d6305b88bbb1bb16e1347a0fcdc609a5.png](https://img-blog.csdnimg.cn/img_convert/d6305b88bbb1bb16e1347a0fcdc609a5.png)
分析:以上结果中显示,每个同学的学号、姓名和分数。首先必须从scholarship表中查询出一等奖学金要求的最低分,我们可以看出一等奖最低分为90分,二等奖为80分,三等奖为70分。然后再从computer_stu表中查询出那些学生的分数高于这个最低分。
select id,name,score from computer_stu where score>=(select score from scholarship where level=1);
![fe0d28cc37887e16e2bd94e8760943f4.png](https://img-blog.csdnimg.cn/img_convert/fe0d28cc37887e16e2bd94e8760943f4.png)
示例:下面我们在department表中查询那些部门没有年龄为24岁的员工。先查一下employee表和department表进行对比。
![aed4f733714400f251a64042d1754b96.png](https://img-blog.csdnimg.cn/img_convert/aed4f733714400f251a64042d1754b96.png)
![64fa11e00294db6506b06773926bbfbb.png](https://img-blog.csdnimg.cn/img_convert/64fa11e00294db6506b06773926bbfbb.png)
分析:从employee表中可以看出,只有部门号d_id为1001的部门有员工的年龄为24岁。而部门名称存在department表中,只有根据部门号来查找想要部门的名称。因此需要先从employee表中查询那个人为24岁,取出这个人的部门号,然后在department表中查询与该部门号不同的部门。
select d_id,d_name from department where d_id!=(select d_id from employee where age=24);
![5caa12ff250249f3b27410cbc813e266.png](https://img-blog.csdnimg.cn/img_convert/5caa12ff250249f3b27410cbc813e266.png)
3. 带exists关键字的子查询
exists关键字表示存在。使用exists关键字时,内层查询语句不返回查询的记录,而是返回一个真假值。如果内层查询语句满足条件则返回一个真值,否则,返回假值。当返回的值为true时,外层查询语句进行查询,当返回false时,外层查询语句不进行查询或者是返回空值。
下面如果department表中存在d_id取值为1003的记录,则查询employee表的记录。
select * from employee where exists(select d_name from department where d_id=1003);
![4aa4188499c0dd789431cebb0fc62272.png](https://img-blog.csdnimg.cn/img_convert/4aa4188499c0dd789431cebb0fc62272.png)
下面我们查看department表中,如果存在d_id取值为1004的记录,则查询employee表的记录。
select * from employee where exists (select d_id from department where d_id =1004);
![edbf8d2482ffbfb9ac0fd132e37ceefb.png](https://img-blog.csdnimg.cn/img_convert/edbf8d2482ffbfb9ac0fd132e37ceefb.png)
查询结果显示为空。因为department表中不存在d_id=1004的记录。
注:exists关键字可以与其他的查询条件一起使用。条件表达式与exists关键字之间用and或者or来连接;
示例:如果department表中存在d_id取值为1003的记录,则查询employee表中age大于24的记录。
select * from employee where age>24 and exists (select d_id from department where d_id=1003);
![260763a455490fa4331b3539813f4e46.png](https://img-blog.csdnimg.cn/img_convert/260763a455490fa4331b3539813f4e46.png)
用not exists查询,结果相反
select * from employee where age>24 and exists(select d_id from department where d_id=1003);
![2523521f61a712833527f1b47963a3a0.png](https://img-blog.csdnimg.cn/img_convert/2523521f61a712833527f1b47963a3a0.png)
4. 带any关键字的子查询
any关键字表示满足其中任一条件。使用any关键字是,只要满足内层查询语句返回的结果中的任何一个,就可以通过该条件来执行外层查询语句。
下面我们从computer_stu表中查询出那些同学可以获得奖学金。奖学金信息存储在scholarship表中。先查看一下computer_stu表和scholarship表。
scholarship表
![2b65a0ffe8d26aac1259f62c8428ea63.png](https://img-blog.csdnimg.cn/img_convert/2b65a0ffe8d26aac1259f62c8428ea63.png)
computer表
![427e9dc3746bac96c78f1d2a9aea597c.png](https://img-blog.csdnimg.cn/img_convert/427e9dc3746bac96c78f1d2a9aea597c.png)
分析:先需要从scholarship表中查询出各种奖学金的最低分。然后从computer_stu表中查询那些人的分数高于其中任何一个奖学金的最低分;
select * from computer_stu where score>=any(select score from scholarship);
![32b693ec4b1e02a44c696224ba5fa52b.png](https://img-blog.csdnimg.cn/img_convert/32b693ec4b1e02a44c696224ba5fa52b.png)
5. 带all关键字的子查询
all关键字表示满足所有条件。使用all关键字是,只有满足内层查询语句返回的所有结果,才可以执行外城查询语句。
下面从computer_stu表中查询出那些同学可以获得一等奖学金。奖学金的信息存储在scholarship表中。
分析:先需要从scholarship表中查询出各种奖学金的最低分,然后,从computer_stu表中查询那些人的分数高于所有奖学金的最低分。
select * from computer_stu where score>=all(select score from scholarship);
![3d4e0debfa0db2362b0f5bd341a5ee89.png](https://img-blog.csdnimg.cn/img_convert/3d4e0debfa0db2362b0f5bd341a5ee89.png)
注:any关键字和all关键字的使用方式一样。但是两者有很大的区别,使用any关键字时,只要满足内层查询语句返回的结果中的任何一个,就可以通过该条件来执行外层查询语句。而all关键字恰好相反,只有满足内层查询语句返回的所有结果,才可以执行外层查询。