SQL语句练习题4 嵌套查询

【一句话概括本文】

本文旨在通过mysql实验的方式完成10道嵌套查询语言题。

【上题目】

嵌套查询

  1. 检索选修‘c01’课程的女学生的姓名
  2. 检索学号比王丽同学小,而年龄比她大的学生姓名
  3. 检索20210002同学不学的课程的课程号。
  4. 检索王丽同学不学的课程的课程号。(in和exists两种方法)
  5. 检索至少选修计算机系所开课程2门以上的女学生姓名
  6. 查询没有同时选修c02,c03,c04的同学的学号。
  7. 查询既选修了‘数据库原理’又选修了‘操作系统’的学生的姓名及学号。
  8. 查询既没有选修‘数据库原理’又没有选修‘操作系统’的学生的姓名及学号。(使用子查询和集合运算两种方法实现)
  9. 检索选修了全部课程的学生的学号与姓名。
  10. 检索选修计算机系所开全部课程的学生的学号与姓名。

【上解析】

1.检索选修‘c01’课程的女学生的姓名

方法一:多表查询

SELECT  s.Sno, s.Sname, c.Cno, c.Cname 

FROM sc,student AS s,department AS d, course AS c 

WHERE s.sno=sc.sno AND s.deptNo=d.deptno AND sc.cno=c.cno

AND c.cno='c01' AND s.ssex='女'

运行结果:

0ebf06e5cc3044e1b61471bcad3fc584.png

方法二:嵌套查询

SELECT sname FROM student

WHERE ssex='女' and sno IN(

SELECT sno

FROM sc

WHERE cno ='c01'

)

运行结果:

37d1e2a36b9e4f8181a687406aefd97f.png

2.检索学号比王丽同学小,而年龄比她大的学生姓名

SELECT sname FROM student

WHERE  

sno <(

SELECT sno

FROM student

WHERE sname='王丽'

)

AND

sage>(

SELECT sage

FROM student

WHERE sname='王丽'

);

SELECT*FROM student;

运行结果:

2ec741231c9b4aa5bd1b408a6fd1dc2b.png

3.检索20210002同学不学的课程的课程号。

SELECT cno FROM course

WHERE cno NOT IN (

SELECT cno FROM sc

WHERE sno='20210002'

)

运行结果:

137bb24f86754e20861ce91455871cbe.png

4.检索王丽同学不学的课程的课程号。(in和exists两种方法)

方法一:in方法

SELECT cno FROM course

WHERE cno NOT IN (

SELECT cno FROM sc

WHERE sno IN(

SELECT sno FROM student

WHERE sname='王丽'

)

)

运行结果:

81389753657b4f02b56bd3a3e55d0b73.png

方法二:exists方法

#下面这个不正确。错因:cno=sc.cno处错误

#因为cno会认为是内部变量,也就是sc的cno,那么就没有起到效果

SELECT cno FROM course

WHERE NOT EXISTS(

#王丽同学要学的

SELECT * FROM sc

WHERE sno IN(

SELECT sno FROM student

WHERE sname='王丽'

)

AND cno=sc.cno

)

#下面这个正确

SELECT cno FROM course

WHERE NOT EXISTS(

#王丽同学要学的

SELECT * FROM sc

WHERE sno IN(

SELECT sno FROM student

WHERE sname='王丽'

)

AND course.cno=sc.cno

)

运行结果:

c9ce542ca47d447ca2f5c3f56269abac.png

5.检索至少选修计算机系所开课程2门以上的女学生姓名

#首先插入数据

#现在计算机系所开课程只有2门,无论怎样查询结果都为空集。所以增加2门课程

#建议是数据库和操作系统,因为后面的题目可以用

INSERT INTO sc (Sno, Cno, Grade) VALUES ('20210001', 'C06', 98);

INSERT INTO sc (Sno, Cno, Grade) VALUES ('20210002', 'C06', 67);

INSERT INTO sc (Sno, Cno, Grade) VALUES ('20210003', 'C06', 82);

INSERT INTO sc (Sno, Cno, Grade) VALUES ('20210004', 'C06', 49);

INSERT INTO course (Cno, Cname, Pno, Credit, Deptno) VALUES ('C06', '离散数学', NULL, 3, 1);

运行结果:

a5c70fdb6bc3402ca4894eba4960343c.png

#错误的写法。group by位置错误

SELECT * FROM student s

WHERE ssex='女' 

AND sno IN(

SELECT sno FROM sc

WHERE  cno IN(

SELECT cno FROM course

WHERE deptno IN(

SELECT deptno from department

WHERE deptname='计算机系'

)

)

)

GROUP BY sno

HAVING COUNT(*)>2

#正确的写法

SELECT sname FROM student s

WHERE ssex='女' 

AND sno IN(

SELECT sno FROM sc

WHERE  cno IN(

SELECT cno FROM course

WHERE deptno IN(

SELECT deptno from department

WHERE deptname='计算机系'

)

)

GROUP BY sno

HAVING COUNT(*)>2

)

a9c977a43e3e4f3aba3c0fa8bc952802.png

6.查询没有同时选修c02,c03,c04的同学的学号。

方法一:嵌套查询

SELECT student.sno,student.sname

FROM student

WHERE student.sno NOT IN (

    SELECT sc.sno

    FROM sc

    WHERE sc.cno = 'c02'

    AND sc.sno IN (

        SELECT sc.sno

        FROM sc

        WHERE sc.cno = 'c03'

    )

    AND sc.sno IN (

        SELECT sc.sno

        FROM sc

        WHERE sc.cno = 'c04'

    )

)

45f82d1967454c5ead4ce1f61a976be0.png

方法二:集合查询

#里面的select进行的集合合并与subquery很重要

SELECT sno

FROM student

WHERE sno NOT IN (

    SELECT sno

    FROM (

        SELECT sno

        FROM sc

        WHERE cno = 'c02'

        

        INTERSECT

        

        SELECT sno

        FROM sc

        WHERE cno = 'c03'

        

        INTERSECT

        

        SELECT sno

        FROM sc

        WHERE cno = 'c04'

    ) AS subquery

);

d77a7ea8f7c0477b92588e31fd480aae.png

7.查询既选修了‘数据库原理’又选修了‘操作系统’的学生的姓名及学号。

SELECT sno,sname

FROM student

WHERE sno  IN (

    SELECT sno

    FROM (

        SELECT sno

        FROM sc

        WHERE cno IN (

                   SELECT cno

                           FROM course

                                WHERE cname='数据库原理'

 )    

        INTERSECT

SELECT sno

        FROM sc

        WHERE cno IN (

                   SELECT cno

                           FROM course

                                WHERE cname='操作系统'

 )

    ) AS subquery

);

8.查询没有选修‘数据库原理’又没有选修‘操作系统’的学生的姓名及学号。(使用子查询和集合运算两种方法实现)

6、7、8是同类型题目。作者建议读者不要光看不练,自己动手做一个,把结果发在评论区吧!

一起进步!

9.检索选修了全部课程的学生的学号与姓名。

#ai逻辑1 not esists

SELECT s.Sname, s.Sno

FROM student s

WHERE NOT EXISTS (

    SELECT *

    FROM course c

    WHERE NOT EXISTS (

        SELECT *

        FROM sc

        WHERE sc.Sno = s.Sno AND sc.Cno = c.Cno

    )

);

#ai 逻辑2 group by+having

SELECT s.Sname, s.Sno

FROM student s

JOIN sc ON s.Sno = sc.Sno

GROUP BY s.Sno, s.Sname

HAVING COUNT(DISTINCT sc.Cno) = (SELECT COUNT(DISTINCT Cno) FROM course);

#ai 逻辑3 不使用exists,试着使用all。但是还是需要group by和having

SELECT s.Sname, s.Sno

FROM student s

WHERE s.Sno = ALL (

    SELECT sc.Sno

    FROM sc

    GROUP BY sc.Sno

    HAVING COUNT(DISTINCT sc.Cno) = (SELECT COUNT(*) FROM course)

);

运行结果:

74bd772256914c3b8c42856d41d4ca64.png

10.检索选修计算机系所开全部课程的学生的学号与姓名。

SELECT s.Sname, s.Sno

FROM student s

JOIN department d ON s.deptNo = d.deptNo

WHERE d.deptName = '计算机系' AND NOT EXISTS (

    SELECT *

    FROM course c

    WHERE c.Deptno = d.deptNo AND NOT EXISTS (

        SELECT *

        FROM sc

        WHERE sc.Sno = s.Sno AND sc.Cno = c.Cno

    )

);

运行结果:

77b586f31a1a4d6ab178552b59bbb389.png

恭喜您又进步了,本文约3600字!学完本文,您掌握了6个以上嵌套查询语句,特别是in()和集合运算intersect的使用。

非常非常非常非常非常感谢您的观看!如您发现任何错误,欢迎在评论区批评指教!

致谢:

本文特别感谢

@春天的小帆船

@Joker_XWX

提供的参考资料。

没有这些帮助,这篇作品也很难诞生了

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值