真正理解exists 和not exists

真正理解exists 和not exists前言今天看了下mysql训练题,其中有一题很有意思。​    下面也写了sql解答,使用了group_concat()函数,这个函数是分组后将一组的字段(比如name)拼接在一起,默认以逗号分隔。这个思路可以,但是在成绩表插入信息时的顺序是乱的,那又怎么查。    我然后看了几个其他人的答案,还有的用课程数作比较的,写的很乱很杂。想了一会,觉得使用notexists解答是可以的。exists与notexist.

大家好,又见面了,我是你们的朋友全栈君。如果您正在找激活码,请点击查看最新教程,关注关注公众号 “全栈程序员社区” 获取激活教程,可能之前旧版本教程已经失效.最新Idea2022.1教程亲测有效,一键激活。

Jetbrains全系列IDE使用 1年只要46元 售后保障 童叟无欺

前言

今天看了下mysql训练题,其中有一题很有意思。

在这里插入图片描述

​     下面也写了sql解答,使用了group_concat()函数,这个函数是分组后将一组的字段(比如name)拼接在一起,默认以逗号分隔。这个思路可以,但是在成绩表插入信息时的顺序是乱的,那又怎么查。

    我然后看了几个其他人的答案,还有的用课程数作比较的,写的很乱很杂。想了一会,觉得使用not exists解答是可以的。

exists与not exists

原理解释:

exists(sql返回结果集为真)

not exists(sql不返回结果集为真或返回结果集为假)

这看的挺懵逼的,这里详细的解释下exists和not exists的原理和用法吧。

select * from A where not exists(select * from B where A.id = B.id);
select * from A where exists(select * from B where A.id = B.id);

    首先我们要知道sql语句使用了exists或not exists后的执行顺序,注意,是先执行外查询再执行内查询。这和我们学的子查询概念就“冲突了”,特别是刚学完子查询后再学exists,简直让人崩溃。

详细步骤(使用exists):

1,首先执行外查询select * from A,然后从外查询的数据取出一条数据传给内查询。

2,内查询执行select * from B,外查询传入的数据和内查询获得数据根据where后面的条件做匹对,如果存在数据满足A.id=B.id则返回true,如果一条都不满足则返回false。

3,内查询返回true,则外查询的这行数据保留,反之内查询返回false则外查询的这行数据不显示。外查询的所有数据逐行查询匹对。

not exists和exists的用法相反,就不继续啰嗦了。

案例分析

还是根据上面的那道题做分析来看看not exists或exists是如何用的吧。

# 学生表
CREATE TABLE `Student`(
    `s_id` VARCHAR(20),
    `s_name` VARCHAR(20) NOT NULL DEFAULT '',
    `s_birth` VARCHAR(20) NOT NULL DEFAULT '',
    `s_sex` VARCHAR(10) NOT NULL DEFAULT '',
    PRIMARY KEY(`s_id`)
);
# 课程表
CREATE TABLE `Course`(
    `c_id`  VARCHAR(20),
    `c_name` VARCHAR(20) NOT NULL DEFAULT '',
    `t_id` VARCHAR(20) NOT NULL,
    PRIMARY KEY(`c_id`)
);
# 教师表
CREATE TABLE `Teacher`(
    `t_id` VARCHAR(20),
    `t_name` VARCHAR(20) NOT NULL DEFAULT '',
    PRIMARY KEY(`t_id`)
);
# 成绩表
CREATE TABLE `Score`(
    `s_id` VARCHAR(20),
    `c_id`  VARCHAR(20),
    `s_score` INT(3),
    PRIMARY KEY(`s_id`,`c_id`)
);
# 插入学生表测试数据
insert into Student values('01' , '赵雷' , '1990-01-01' , '男');
insert into Student values('02' , '钱电' , '1990-12-21' , '男');
insert into Student values('03' , '孙风' , '1990-05-20' , '男');
insert into Student values('04' , '李云' , '1990-08-06' , '男');
insert into Student values('05' , '周梅' , '1991-12-01' , '女');
insert into Student values('06' , '吴兰' , '1992-03-01' , '女');
insert into Student values('07' , '郑竹' , '1989-07-01' , '女');
insert into Student values('08' , '王菊' , '1990-01-20' , '女');
#课程表测试数据
insert into Course values('01' , '语文' , '02');
insert into Course values('02' , '数学' , '01');
insert into Course values('03' , '英语' , '03');
# 教师表测试数据
insert into Teacher values('01' , '张三');
insert into Teacher values('02' , '李四');
insert into Teacher values('03' , '王五');
#成绩表测试数据
insert into Score values('01' , '01' , 80);
insert into Score values('01' , '02' , 90);
insert into Score values('01' , '03' , 99);
insert into Score values('02' , '01' , 70);
insert into Score values('02' , '02' , 60);
insert into Score values('02' , '03' , 80);
insert into Score values('03' , '01' , 80);
insert into Score values('03' , '02' , 80);
insert into Score values('03' , '03' , 80);
insert into Score values('04' , '01' , 50);
insert into Score values('04' , '02' , 30);
insert into Score values('04' , '03' , 20);
insert into Score values('05' , '01' , 76);
insert into Score values('05' , '02' , 87);
insert into Score values('06' , '01' , 31);
insert into Score values('06' , '03' , 34);
insert into Score values('07' , '02' , 89);
insert into Score values('07' , '03' , 98);

    题目是查询和”01″号的同学学习的课程完全相同的其他同学的信息,直接做确实有点麻烦,我们可以先做做这题:查看学了所有课程的同学的信息。

    学了所有课程的同学的信息,那不就是这些同学没有一门课程没有学吗。

select * from Student st where not exists(select * from Course c 
where not exists(select * from Score sc where sc.c_id = c.c_id 
and sc.s_id = st.s_id));

在这里插入图片描述

    然后我们再回过来看这题,是不是和刚才的题一模一样,只不过把所有的课程换成01同学学的课程。

select * from Student st where not exists(select * from
( select s2.c_id as c_id from Student s1 
inner join Score s2 on s1.s_id = s2.s_id where s1.s_id = 01) t 
where  not exists (select * from Score sc 
where sc.c_id = t.c_id and sc.s_id = st.s_id and st.s_id != 01));

在这里插入图片描述

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

发布者:全栈程序员-用户IM,转载请注明出处:https://javaforall.cn/157832.html原文链接:https://javaforall.cn

【正版授权,激活自己账号】: Jetbrains全家桶Ide使用,1年售后保障,每天仅需1毛

【官方授权 正版激活】: 官方授权 正版激活 支持Jetbrains家族下所有IDE 使用个人JB账号...

(0)
blank

相关推荐

发表回复

您的电子邮箱地址不会被公开。

关注全栈程序员社区公众号