欢迎来到天天文库
浏览记录
ID:34724953
大小:66.18 KB
页数:3页
时间:2019-03-10
《oracle中in与existnotin与notexist的区别》由会员上传分享,免费在线阅读,更多相关内容在工程资料-天天文库。
1、sql语句中in与existnotin与notexist的区别Oracle中in和existsin是把外表和内表作hash连接,而exists是对外表作loop循环,每次loop循环再对内表进行查询。一直以来认为exists比in效率高的说法是不准确的。如果查询的两个表大小相当,那么用in和exists差别不大。如果两个表中一个较小,一个是大表,则子查询表大的用exists,子查询表小的用in:例如:表A(小表),表B(大表)1:select*fromAwhereccin(selectccfromB)效率低,用到了A表上cc列的索引;sele
2、ct*fromAwhereexists(selectccfromBwherecc=A.cc)效率高,用到了B表上cc列的索引。相反的2:select*fromBwhereccin(selectccfromA)效率高,用到了B表上cc列的索引;select*fromBwhereexists(selectccfromAwherecc=B.cc)效率低,用到了A表上cc列的索引。notin和notexists如果查询语句使用了notin那么内外表都进行全表扫描,没有用到索引;而notextsts的子查询依然能用到表上的索引。所以无论那个表大,用no
3、texists都比notin要快。in与=的区别selectnamefromstudentwherenamein('zhang','wang','li','zhao');与selectnamefromstudentwherename='zhang'orname='li'orname='wang'orname='zhao'的结果是相同的。补充notin逻辑上不完全等同于notexists,如果你误用了notin,小心你的程序存在致命的BUG:请看下面的例子:createtablet1(c1number,c2number);createtable
4、t2(c1number,c2number);insertintot1values(1,2);insertintot1values(1,3);insertintot2values(1,2);insertintot2values(1,null);select*fromt1wherec2notin(selectc2fromt2);norowsfoundselect*fromt1wherenotexists(select1fromt2wheret1.c2=t2.c2);c1c213正如所看到的,notin出现了不期望的结果集,存在逻辑错误。如果看一下
5、上述两个select语句的执行计划,也会不同。后者使用了hash_aj。因此,请尽量不要使用notin(它会调用子查询),而尽量使用notexists(它会调用关联子查询)。如果子查询中返回的任意一条记录含有空值,则查询将不返回任何记录,正如上面例子所示。除非子查询字段有非空限制,这时可以使用notin,并且也可以通过提示让它使用hasg_aj或merge_aj连接。
此文档下载收益归作者所有