《数据库原理与开发 教学课件 ppt 作者 赵明砚 单世民 赵凤强 第3章2》由会员分享,可在线阅读,更多相关《数据库原理与开发 教学课件 ppt 作者 赵明砚 单世民 赵凤强 第3章2(105页珍藏版)》请在金锄头文库上搜索。
1、3.3 数据查询,3.3.1单表查询 3.3.2多表查询 3.3.3嵌套查询 3.3.4集合查询 3.3.5视图查询 3.3.6 查询语句小结,3.3.2 多表查询,同时涉及多个表的查询称为连接查询 用来连接两个表的条件称为连接条件或连接谓词 内连接查询:包括等值及非等值连接、自然连接、自身连接 外连接查询 交叉连接查询 最常用的连接查询。交叉连接查询是指内、外连接查询同时出现在一条查询语句的连接查询,书写起来比较复杂,使用量较小。本节只介绍内连接和外连接查询。,连接查询 (续),连接字段 连接谓词中的列名称为连接字段 连接条件中的各连接字段类型必须是可比的,但不必是相同的,1、内连接,内连接
2、是指在多个表中查询满足连接条件的元组,其格式为: SELECT . 列名1, FROM 表名1 INNER JOIN 表名2 ON 也可以写为: SELECT . 列名1, FROM 表名1,表名2 WHERE ,其中连接条件的格式一般为: . 连接条件也可以使用下面形式: . BEDTWEEN . AND . 为了区分表中的属性列,可以给属性列加上表名前缀,但如果属性列名都不相同,可以取消属性列前面的表名前缀。为了方便书写,可以对表取一个别名,其形式与属性列别名类似,即将表的别名写在表名后,用空格隔开。,当连接条件中的运算符为“=”时,称为等值连接。使用其他运算符称为非等值连接。连接条件中的
3、列名称为连接字段。,连接操作的执行过程,在DBMS执行连接操作时,其查找过程如下:首先取表1中第1个元组,然后从头开始扫描表2的每一个元组,逐一查找满足连接条件的元组,找到后就将表1中的第1个元组与该元组拼接起来,形成结果表中一个元组。表2全部扫描完后,再取表1中第2个元组,然后再从头开始扫描表2的每一个元组,逐一查找满足连接条件的元组,找到后就将表1中的第2个元组与该元组拼接起来,形成结果表中的一个元组。重复上述操作,直到表1中的全部元组都处理完毕为止。,【例3-26】 查询每个学生及其选修课程的详细信息。 学生的详细信息存放在Student表中,学生选修课程的详细信息存放在SC表中。本题需
4、要对这两个表进行连接查询,这两个表之间的联系是通过公共属性Sno实现的。 SELECT Student.*, SC.* FROM Student, SC WHERE Student.Sno=SC.Sno; /*将Student与SC中同一学生的元组连接起来*/ 请大家参照书自行写出查询结果,【例3-27】 查询选修了课程名为“数据库”的学生学号和姓名。 思路:学生的学号和姓名要在Student表中查询,课程名是Course表中的属性列,选修课程的学生在SC表中存放,因此本查询涉及Student表、Course表和SC表,是3个表的连接查询。我们再观察一下这3个表,Student表与SC表有共同
5、的属性Sno,Course表和SC表有共同的属性Cno,可以通过这两个相同的属性进行3个表的连接。 SELECT Sno,Sname FROM Student,SC,Course WHERE Student.Sno=SC.Sno AND SC.Cno=Course.Cno AND Course.Cname=数据库;,内连接操作不仅可以在两个表之间进行,也可以是一个表与其自己进行连接,称为表的自身连接。 【例3-28】 查询与“丁林”在同一个系学习的学生。 SELECT S1.Sno, S1.Sname, S1.Sdept FROM Student S1, Student S2 WHERE S1
6、.Sdept=S2.Sdept AND S2.Sname=丁林;,2、外连接,在内连接操作中,只有满足连接条件的元组才能作为结果输出。但有时我们也希望输出那些不满足连接条件的元组信息,这时就需要用外连接操作。如希望查找Student表中每个学生的基本情况及其选课情况,若某个学生没有选课,也输出其基本情况信息,其选课信息为空值即可,这时就需要使用外连接。 外连接又分为:左外连接和右外连接。,其语句格式为: SELECT . 列名1, FROM 表名1 LEFT | RIGHT OUTER JOIN 表名2 ON 其中,LEFT OUTER JOIN称为左外连接,表1中的数据可以全部输出,而表2中
7、的数据必须满足连接条件; RIGHT OUTER JOIN称为右外连接,表2中的数据可以全部输出,而表1中的数据必须满足连接条件。 也可以写为: SELECT . 列名1, FROM 表名1,表名2 WHERE .(+).(+) 其中,(+)在左边称为左外连接,在右边称为右外连接。左外连接是要全部输出连接条件右边的表,右外连接是要全部输出连接条件左边的表。,【例3-29】 查询每个学生及其选修课程的详细信息,包括没有选修课程的学生。 SELECT Student.Sno, Sname, Ssex, Sage, Sdept, Cno, Grade FROM Student LEFT OUTER
8、JOIN SC ON Student.Sno=SC.Sno;,3.3 数据查询,3.3.1单表查询 3.3.2多表查询 3.3.3嵌套查询 3.3.4集合查询 3.3.5视图查询 3.3.6 查询语句小结,3.3.3 嵌套查询,在SQL语言中,一个SELECT-FROM-MHERE语句称为一个查询块。将一个查询块嵌套在另一个SQL语句中的情况很多,其中最常用的是将一个查询块嵌套到另一个查询块的WHERE子句或HAVING短语的条件中,我们称为嵌套查询。 外层的查询块称为父查询,内层的查询块称为子查询。前面提到过ORDER BY子句只能应用于最终结果,因此子查询语句中不能使用ORDER BY子句
9、。,嵌套查询的求解方法有两种:一种是由内层查询向外层查询处理,称为不相关子查询;另一种是由外层查询向内层查询处理,称为相关子查询。不相关子查询的子查询条件不依赖于父查询,子查询的结果用于建立其父查询的查找条件。相关子查询的查询条件依赖于父查询的某个属性值。 嵌套查询以层层嵌套的方式来构造SQL语句,体现了SQL语言的“结构化”特点。,嵌套查询(续),嵌套查询 一个SELECT-FROM-WHERE语句称为一个查询块 将一个查询块嵌套在另一个查询块的WHERE子句或HAVING短语的条件中的查询称为嵌套查询,嵌套查询(续),SELECT Sname 外层查询/父查询 FROM Student W
10、HERE Sno IN (SELECT Sno 内层查询/子查询 FROM SC WHERE Cno= 2 );,嵌套查询(续),子查询的限制 不能使用ORDER BY子句 层层嵌套方式反映了 SQL语言的结构化 有些嵌套查询可以用连接运算替代,嵌套查询分类,不相关子查询 子查询的查询条件不依赖于父查询 相关子查询 子查询的查询条件依赖于父查询,嵌套查询求解方法,不相关子查询 是由里向外逐层处理。即每个子查询在 上一级查询处理之前求解,子查询的结果 用于建立其父查询的查找条件。,嵌套查询求解方法(续),相关子查询 首先取外层查询中表的第一个元组,根据它与内层查询相关的属性值处理内层查询,若WH
11、ERE子句返回值为真,则取此元组放入结果表; 然后再取外层表的下一个元组; 重复这一过程,直至外层表全部检查完为止。,引出子查询的谓词,带有IN谓词的子查询 带有比较运算符的子查询 带有EXISTS谓词的子查询,1、带有IN谓词的子查询,【例3-30】 查询与“丁林”在同一个系学习的学生。 思路:应该首先查找丁林在哪个系学习,然后再查找在该系学习的学生。我们能看出第一步的查询是第二步的条件。因此通过分步查询可构建嵌套查询。 (1)确定“丁林”所在系名。 SELECT Student WHERE Sname=丁林;,带有IN谓词的子查询(续),(2)查找所有在该系学习的学生。 SELECT Sn
12、o, Sname, Sdept FROM Student WHERE Sdept=信息系;,将第一步作为内层查询,也就是子查询,构造嵌套查询,SQL语句如下: SELECT Sname, Sdept FROM Student S1 WHERE S1.Sdept IN (SELECT Sdept FROM Student S2 WHERE S2. Sname=丁林); 由于父查询和子查询均引用了Student表,可以像自身连接那样通过别名将父查询和子查询中的Student表区分开。 DBMS求解该查询时,实际上也要分步去做,本例中的查询也可以用自身连接来完成,如例3-27所示。同一个查询可能有多
13、种方法,但不同的方法其执行效率可能会有差别,甚至会差别很大。,【例3-31】 查询选修了课程名为“数据库”的学生学号和姓名。 思路:因为SC表中只有课程号,而没有课程名,因此要做此查询,可以首先在Course表中找到“数据库”课程的课程号Cno,再通过Cno在SC表找到选修该课程号的学生学号Sno,因为SC中没有学生姓名,所以只能再通过Sno在Student表中查找学生姓名。按照上述步骤使用嵌套查询语句如下: SELECT Sno,Sname FROM Student WHERE Sno IN (SELECT Sno FROM SC WHERE Cno IN (SELECT Cno FROM
14、Course WHERE Cname=数据库) 本查询可以用连接查询实现,但这里需要注意:并不是所有的嵌套查询都能用连接查询替代。,2、带有比较运算符的子查询,当能确切知道内层查询返回单值时,可用比较运算符(,=,)。 与ANY或ALL谓词配合使用,【例3-32】 查询数学系中比信息系某一学生年龄小的学生姓名和年龄。 SELECT Sname, Sage FROM Student WHERE Sdept=数学系 AND Sage ANY(SELECT Sage FROM Student WHERE Sdept=信息系) 本查询也可以用比较运算符和集函数来实现。首先用子查询找出信息系中学生的最大
15、年龄,然后在父查询中查询所有数学系且年龄小于信息系中最大年龄的学生姓名及年龄。请大家自行写出。,带有ANY或ALL谓词的子查询,谓词语义 ANY:任意一个值 ALL:所有值,带有ANY或ALL谓词的子查询(续),需要配合使用比较运算符 ANY 大于子查询结果中的某个值 ALL 大于子查询结果中的所有值 = ANY 大于等于子查询结果中的某个值 = ALL 大于等于子查询结果中的所有值 )ANY 不等于子查询结果中的某个值 !=(或)ALL 不等于子查询结果中的任何一个值,带有ANY或ALL谓词的子查询(续),【例3-33】 查询数学系中比信息系所有学生年龄都小的学生姓名及年龄。 SELECT
16、Sage FROM Student WHERE Sdept=数学系 AND SageALL (SELECT Sage FROM Student WHERE Sdept=信息系) 请大家思考将例3-33用比较运算符与集函数来实现。,带有ANY或ALL谓词的子查询(续),ANY和ALL谓词有时可以用集函数实现 ANY与ALL与集函数的对应关系,带有ANY或ALL谓词的子查询(续),用集函数实现子查询通常比直接用ANY或ALL查询效率要高,因为前者通常能够减少比较次数,3、带有EXISTS谓词的子查询,有时我们在查询时并不要求返回确切的值,而只是需要判断是否存在,这时就需要用EXISTS为此引起嵌套查询。由EXISTS谓词引起的嵌套查询不返回任何数据,只产生逻辑真值“true”或逻辑假值“fales”,代表存在或者不存在。由于