嵌套查询(一)-谓词IN、量词ANY、量词ALL

一、在多个表之间进行数据查询,除了可以使用连接查询之外,也可以使用嵌套查询,那么什么是嵌套查询呢?如何使用嵌套查询呢?

1、将一个SELECT-FROM查询,嵌套在另一个SELECT查询语句中,那么这个SELECT-FROM查询就叫嵌套查询或者子查询,被嵌套的上层查询被称为父查询,在子查询中还可以继续嵌入子查询,构成多层嵌套查询,一个查询的结果可能是一个关系,即元组的集合,也可能是一个值,即聚集函数的结果,因此,子查询既可以嵌套在其父查询的SELECT子句的目标列表达式中参与计算,也可以嵌套在其父查询的FROM子句中作为进一步查询的对象,还可以嵌套在其父查询的WHERE子句或HAVING短语的条件表达式中,作为进一步查询的条件,不同的DBMS对嵌套查询的支持程度不同

2、下面介绍几种常用的嵌套查询的使用方式

二、谓词IN实现嵌套查询

IN谓词用于判断一个值是否属于一个集合,其运算结果是一个布尔值

E 【NOT】 IN (V1,V2,...,Vn)

1、将子查询放在IN谓词后面的小括号中,使用子查询查询出来的结果集,实际上还是一个表

2、独立子查询:子查询的结果不依赖于父查询

(1)举例:查询选修了"003"课程的学生姓名

sql 复制代码
select sN
from s
where sNo in (select sNo from sC where cNo='003')

该查询需求也可以使用连接查询满足,但是从DBMS对SQL语句的查询语句的处理方式来看,嵌套查询语句更有利于生成优化的查询执行方案。

(2)逻辑运算符NOT的使用,举例:查询没有选修"003"课程的学生姓名

sql 复制代码
select sN
from s
where sNo not in (select sNo from sC where cNo='003')

错误实例:不可以使用连接查询

sql 复制代码
select sN
from s,sC
where s.sNo=sC.sNo and sC.cNo!='003'

原因:嫦娥不仅选修了003的课程,还选修了其它的课程

三、比较操作符实现嵌套查询

当嵌套查询的结果是一个值是,该嵌套查询可以嵌套在WHERE子句的元组条件选择表达式中

1、举例1:查询选修"003"课程的成绩高于刘备的学生的学号和成绩

sql 复制代码
use XSXK;
select sNo,grade
from sC
where cNo='003' and grade>(
 select grade
 from sC
 where cNo='003' and sNo in(
   select sNo
   from s
   where sN='刘备'
 )
)

这是一个多层嵌套查询,并且每一个子查询都是一个独立子查询

2、举例2:查询每个学生所修课程成绩超过其所有选课平均成绩的学号和课程号

sql 复制代码
use XSXK;
select sC1.sNo,sC1.cNo
from sC sC1
where grade>(
select avg(sC2.grade)
from sC sC2
where sC2.sNo=sC1.sNo
)

(1)这里的子查询结果与父查询的当前元组有关,这种查询被称为相关子查询

(2)在相关子查询中,如果涉及到了父查询所用到的表,往往要对这两个表至少一个进行重命名操作,以便标识不同的元组

四、使用量词ANY或ALL实现嵌套查询

1、在有些DBMS中,如果子查询的结果是一个集合,还可以使用ANY或ALL与比较符配合来实现嵌套查询

2、ANY(子查询)

ANY的语义为查询结果中的某个值,当子查询结果中有某一个值满足比较运算符,比较运算结果则为真

3、ALL(子查询)

ALL的语义为查询结果中的所有值,当子查询结果中的每一个值都满足比较运算符,比较运算结果才为真。

4、举例1:查询其它院系中比数计学院某个学生年龄小的学生

sql 复制代码
select *
from s
where sD!='数计学院' and  sB > any(
select sB
from s
where sD='数计学院'
)

5、举例2:查询其它院系中比数计学院学生年龄都小的学生

sql 复制代码
select *
from s
where sD!='数计学院' and  sB > all(
select sB
from s
where sD='数计学院'
)

6、量词ANY或ALL与比较运算符配合的功能也可以用谓词IN或用聚集函数与与比较符配合来实现

(1)当子查询的结果是一个集合而不是一个值时,比较运算符前的值肯定会不等于查询结果中的某个值,那么比较运算符不能于ANY结果永真,作为父查询的条件没有意义

(2)举例1:查询其它院系中比数计学院某个学生年龄小的学生

sql 复制代码
select *
from s
where sD!='数计学院' and  sB > (
select min(sB)
from s
where sD='数计学院'
)

(3)举例2:查询其它院系中比数计学院学生年龄都小的学生

sql 复制代码
select *
from s
where sD!='数计学院' and  sB > (
select max(sB)
from s
where sD='数计学院'
)
相关推荐
难以触及的高度17 分钟前
mysql中between and怎么用
数据库·mysql
Jacky(易小天)31 分钟前
MongoDB比较查询操作符中英对照表及实例详解
数据库·mongodb·typescript·比较操作符
Karoku0661 小时前
【企业级分布式系统】ELK优化
运维·服务器·数据库·elk·elasticsearch
莫叫石榴姐1 小时前
数据科学与SQL:组距分组分析 | 区间分布问题
大数据·人工智能·sql·深度学习·算法·机器学习·数据挖掘
小技与小术2 小时前
数据库表设计范式
数据库·mysql
安迁岚2 小时前
【SQL Server】华中农业大学空间数据库实验报告 实验三 数据操作
运维·服务器·数据库·sql·mysql
安迁岚2 小时前
【SQL Server】华中农业大学空间数据库实验报告 实验九 触发器
数据库·sql·mysql·oracle·实验报告
Loganer2 小时前
MongoDB分片集群搭建
数据库·mongodb
LKID体3 小时前
Python操作neo4j库py2neo使用之创建和查询(二)
数据库·python·neo4j
刘大浪3 小时前
后端数据增删改查基于Springboot+mybatis mysql 时间根据当时时间自动填充,数据库连接查询不一致,mysql数据库连接不好用
数据库·spring boot·mybatis