数据库学习7 — 嵌套查询

章节3.4.3

嵌套查询

  • 1.带有IN谓词的子查询
  • 2.带有比较运算符的子查询
  • 3.带有ANY(SOME)或ALL谓词的子查询
    • 1)比较运算符
    • 2)ANY(或SOME)、ALL谓词与聚集函数、IN谓词的等价转换关系表
  • 4. 带有 EXISTS 谓词的子查询

在SQL语言中,一个SELECT-FROM-WHERE 短句称为查询块。一个查询语句块嵌套在另外一个查询块的where子句中,称为嵌套查询。其中外层查询也称为父查询,外层查询。内层查询也称子查询,内层查询。

1.带有IN谓词的子查询

子查询结果往往是一个集合,所以谓词 IN 是嵌套查询中最经常使用的谓词。

例题1:查询与“刘晨”在同一个系学习的学生。

①确定“刘晨”所在系名

SELECT Sdept
FROM Student
WHERE Sname = '刘晨';
//结果为 CS

②查找所有在CS系里学习的学生

SELECT Sno,Sname,Sdept
FROM Student
WHERE Sdept = 'CS';

完整代码:

SELECT Sno,Sname,Sdept
FROM Student
WHERE Sdept IN
	(
		SELECT Sdept
		FROM Student
		WHERE Sname = '刘晨');

在本例中,子查询的查询条件不依赖于父查询,称为不相关子查询

例题2:查询选修了课程名为“信息系统”的学生学号和姓名。

  SELECT Sno,Sname                
  FROM Student                          
  WHERE Sno IN
         (SELECT Sno                     
          FROM SC                        
          WHERE Cno IN
                 (SELECT Cno             
                   FROM Course           
                   WHERE Cname= '信息系统')
          );

查询涉及多个关系时,用嵌套查询逐步求解层次清楚,易于构造,具有结构化程序设计的优点。

2.带有比较运算符的子查询

带有比较运算符的子查询是指父查询和子查询使用比较运算符连接的嵌套查询。当知道内层循环返回的是单个值时,可以用>、<、=、>=、<=、!=、<>等比较运算符。

例题3:找出每个学生超过他选修课程平均成绩的课程号。

SELECT Sno,Cno
FROM SC x
WHERE Grade >=(SELECT AVG(Grade) 
               FROM  SC y
               WHERE y.Sno=x.Sno);

子查询中查询条件依赖于外层查询中的某个值,所以子查询的处理不只一次,要反复求值,以供外层查询使用,这类查询称为相关子查询

3.带有ANY(SOME)或ALL谓词的子查询

子查询返回单值时可以用比较运算符,但返回多值时要用ANY(有的系统用SOME)或ALL谓词修饰符。而使用ANY或ALL谓词时则必须同时使用比较运算符。

1)比较运算符

数据库学习7 — 嵌套查询_第1张图片
例题4:查询非计算机科学系中比计算机科学系任意一个学生年龄小的学生姓名和年龄。

SELECT Sname,Sage
FROM Student
WHERE Sage < ANY (SELECT Sage
                  FROM Student
                  WHERE Sdept= 'CS')
 AND Sdept <> 'CS ';

例题5:查询非计算机科学系中比计算机科学系所有学生年龄都小的学生姓名及年龄。

SELECT Sname,Sage
FROM Student
WHERE Sage < ALL (SELECT Sage
                  FROM Student
                  WHERE Sdept= 'CS')
 AND Sdept <> 'CS ';

2)ANY(或SOME)、ALL谓词与聚集函数、IN谓词的等价转换关系表

在这里插入图片描述

4. 带有 EXISTS 谓词的子查询

带有 EXISTS 谓词的子查询不返回任何数据,只产生逻辑真值 “true” 和逻辑假值 “false”。

例题6:查询所有选修了1号课程的学生姓名。

SELECT Sname
FROM Student
WHERE EXISTS
	(SELECT *
	 FROM SC
	 WHERE Sno=Student.Sno AND Cno='1');

使用存在量词 exists 后,若内层查询结果为非空,则外层的 where 子句返回真值,否则返回假值。

由 exists 引出的子查询,其目标列表达式通常都用 * ,因为带 exists 的子查询只返回真值或假值,给出列名无实际意义。

例题7: 查询没有选修1号课程的学生姓名。

SELECT Sname
FROM Student
WHERE NOT EXISTS
	(SELECT *
	 FROM SC
	 WHERE Sno=Student.Sno AND Cno='1');

使用存在量词 not exists 后,若内层查询结果为空,则外层的 where 子句返回真值,否则返回假值。

例题8:查询选修了全部课程的学生姓名

SELECT Sname
FROM Student
WHERE NOT EXISTS
	(SELECT *
	 FROM Course
	 WHERE NOT EXISTS
	 		(SELECT *
	 		 FROM SC
			 WHERE Sno=Student.Sno AND Cno=Course.Cno));

例题9:查询至少选修了学生201215122选修的全部课程的学生号码

SELECT DISTINCT Sno
FROM SC SCX
WHERE NOT EXISTS
	(SELECT *
	 FROM SC SCY
	 WHERE SCY.Sno='201215122' AND
	 		NOT EXISTS
	 		(SELECT *
	 		 FROM SC SCZ
			 WHERE SCZ.Sno=SCX.Sno AND SCZ.Sno=SCY.Sno));
//结果:201215122

…………………………………………………………………………….

数据库学习7 — 嵌套查询_第2张图片
以上就是文章全部内容,感谢阅读。

你可能感兴趣的:(SQL,server,数据库,sql)