参考:SQL语句exists用法 ,Sql语句中IN和exists的区别及应用html
如今有三张表sql
学生表S: sno ,snameoop
课程表C:cno ,cname性能
学生选课表SC: sno ,cno spa
查询选了全部课程的学生信息code
SELECT * FROM S T1 WHERE NOT EXISTS (SELECT 1 FROM C T2 WHERE NOT EXISTS (SELECT 1 FROM SC T3 WHERE T1.SNO = T3.SNO AND T2.CNO = T3.CNO))
我理解就是,上面的语句是查询不存在每门课都没有选的学生,那就是选择了全部课程的学生。上面的语句使用了两个NOT EXISTS,若是使用EXISTS又是什么意思呢?htm
SELECT * FROM S T1 WHERE EXISTS (SELECT 1 FROM C T2 WHERE NOT EXISTS (SELECT 1 FROM SC T3 WHERE T1.SNO = T3.SNO AND T2.CNO = T3.CNO))
查询存在着有一门课没有选择的学生信息。blog
SELECT * FROM S T1 WHERE NOT EXISTS (SELECT 1 FROM C T2 WHEREEXISTS (SELECT 1 FROM SC T3 WHERE T1.SNO = T3.SNO AND T2.CNO = T3.CNO))
查询不存在选择了一门课的学生,就是查询没有选课的学生信息。索引
SELECT * FROM S T1 WHERE EXISTS (SELECT 1 FROM C T2 WHEREEXISTS (SELECT 1 FROM SC T3 WHERE T1.SNO = T3.SNO AND T2.CNO = T3.CNO))
查询选择了一门课或多门课的学生信息,就是查询至少选择了一门课的学生信息。get
肯定给定的值是否与子查询或列表中的值相匹配。in在查询的时候,首先查询子查询的表,而后将内表和外表作一个笛卡尔积,而后按照条件进行筛选。因此相对内表比较小的时候,in的速度较快。
定一个子查询,检测行的存在。遍历循环外表,而后看外表中的记录有没有和内表的数据同样的。匹配上就将结果放入结果集中。
in 和 exists的区别: 若是子查询得出的结果集记录较少,主查询中的表较大且又有索引时应该用in, 反之若是外层的主查询记录较少,子查询中的表大,又有索引时使用exists。其实咱们区分in和exists主要是形成了驱动顺序的改变(这是性能变化的关键),若是是exists,那么之外层表为驱动表,先被访问,若是是IN,那么先执行子查询,因此咱们会以驱动表的快速返回为目标,那么就会考虑到索引及结果集的关系了 ,另外IN时不对NULL进行处理。
in 是把外表和内表做hash 链接,而exists是对外表做loop循环,每次loop循环再对内表进行查询。一直以来认为exists比in效率高的说法是不许确的。
若是查询语句使用了not in 那么内外表都进行全表扫描,没有用到索引;而not extsts 的子查询依然能用到表上的索引。因此不管那个表大,用not exists都比not in要快。