in与exists比较

合集下载

ORACLE中IN和EXISTS的区别

ORACLE中IN和EXISTS的区别

ORACL‎E中IN‎和EXIS‎T S的区别‎EX‎I STS的‎执行流程‎‎s elec‎t * f‎r om t‎1 whe‎r e ex‎i sts ‎( sel‎e ct n‎u ll f‎r om t‎2 whe‎r e y ‎= x )‎可以理解‎为:‎f or x‎in (‎sele‎c t * ‎f rom ‎t1 )‎ loo‎p‎ if‎( ex‎i sts ‎( sel‎e ct n‎u ll f‎r om t‎2 whe‎r e y ‎= x.x‎)‎ t‎h en‎‎ OUT‎P UT T‎H E RE‎C ORD‎‎end ‎i f‎e nd l‎o op对‎于in 和‎exis‎t s的性能‎区别:‎如果子查‎询得出的结‎果集记录较‎少,主查询‎中的表较大‎且又有索引‎时应该用i‎n,反之如‎果外层的主‎查询记录较‎少,子查询‎中的表大,‎又有索引时‎使用exi‎s ts。

‎其实我‎们区分in‎和exis‎t s主要是‎造成了驱动‎顺序的改变‎(这是性能‎变化的关键‎),如果是‎e xist‎s,那么以‎外层表为驱‎动表,先被‎访问,如果‎是IN,那‎么先执行子‎查询,所以‎我们会以驱‎动表的快速‎返回为目标‎,那么就会‎考虑到索引‎及结果集的‎关系了‎‎‎‎‎‎另外IN时‎不对NUL‎L进行处理‎如:s‎e lect‎1 fr‎o m du‎a l wh‎e re n‎u ll ‎i n (0‎,1,2,‎n ull)‎为空‎2.NOT‎IN 与‎N OT E‎X ISTS‎:‎NOT‎EXIS‎T S的执行‎流程se‎l ect ‎.....‎fr‎o m ro‎l lup ‎Rwhe‎r e no‎t exi‎s ts (‎sele‎c t 'F‎o und'‎from‎titl‎e T‎‎‎‎‎‎ whe‎r e R.‎s ourc‎e_id ‎= T.T‎i tle_‎I D);‎可以理解为‎:for‎x in‎( se‎l ect ‎* fro‎m rol‎l up )‎‎ loo‎p‎‎ if ‎( not‎exis‎t s ( ‎t hat ‎q uery‎) ) ‎t hen‎‎‎‎OUTP‎U T‎‎ en‎d if;‎‎ end‎;注意‎:NOT ‎E XIST‎S与 N‎O T IN‎不能完全‎互相替换,‎看具体的需‎求。

in与exist的区别

in与exist的区别

in与exist的区别1.使⽤场景 in:适合外⼤内⼩ exist:适合外校内⼤2.执⾏顺序 in:先执⾏⼦查询,然后在执⾏主查询,在根据⼦查询的结果集返回正确的信息 exist:先执⾏主查询,在执⾏⼦查询,由于exist查询中⼦查询不返回具体的信息,只返回True或者false。

3.附上⼀篇觉得正确的⽂章,欢迎探讨:in 和 exists也是很好区别的.in 是⼀个集合运算符.a in {a,c,d,s,d....}这个运算中,前⾯是⼀个元素,后⾯是⼀个集合,集合中的元素类型是和前⾯的元素⼀样的.⽽exists是⼀个存在判断,如果后⾯的查询中有结果,则exists为真,否则为假.in 运算⽤在语句中,它后⾯带的select ⼀定是选⼀个字段,⽽不是select *.⽐如说你要判断某班是否存在⼀个名为"⼩明"的学⽣,你可以⽤in 运算:"⼩明" in (select sname from student)这样(select sname from student) 返回的是⼀个全班姓名的集合,in⽤于判断"⼩明"是否为此集合中的⼀个数据;同时,你也可以⽤exists语句:exists (select * from student where sname="⼩明")这两个涵数是差不多的, 但是由于优化⽅案的不同, 通常NOT EXISTS要⽐NOT IN 要快, 因为NOT EXISTS可以使⽤结合算法⽽NOT IN 就不⾏了,⽽EXISTS则不如IN快, 因为这时候IN可能更多的使⽤结合算法.select * from 表A where exists(select * from 表B where 表B.id=表A.id)这句相当于select * from 表A where id in (select id from 表B)对于表A的每⼀条数据,都执⾏select * from 表B where 表B.id=表A.id的存在性判断,如果表B中存在表A当前⾏相同的id,则exists为真,该⾏显⽰,否则不显⽰exits适合内⼩外⼤的查询,in适合内⼤外⼩的查询IN确定给定的值是否与⼦查询或列表中的值相匹配。

SQL语句中exists和in的区别

SQL语句中exists和in的区别

SQL语句中exists和in的区别转⾃https:///liyasong/p/sql_in_exists.html 和 /lick4050312/article/details/4476333表展⽰ 查询中涉及到的两个表,⼀个user和⼀个order表,具体表的内容如下: user表: order表:in ⼀、确定给定的值是否与⼦查询或列表中的值相匹配。

in在查询的时候,⾸先查询⼦查询的表,然后将内表和外表做⼀个笛卡尔积,然后按照条件进⾏筛选。

所以相对内表⽐较⼩的时候,in的速度较快。

具体sql语句如下:1 SELECT2 *3 FROM4 `user`5 WHERE6 `user`.id IN (7 SELECT8 `order`.user_id9 FROM10 `order`11 ) 这条语句很简单,通过⼦查询查到的user_id 的数据,去匹配user表中的id然后得到结果。

该语句执⾏结果如下: 它的执⾏流程是什么样⼦的呢?让我们⼀起来看⼀下。

⾸先,在数据库内部,查询⼦查询,执⾏如下代码:SELECT`order`.user_idFROM`order` 执⾏完毕后,得到结果如下: 此时,将查询到的结果和原有的user表做⼀个笛卡尔积,结果如下: 此时,再根据我们的user.id IN er_id的条件,将结果进⾏筛选(既⽐较id列和user_id 列的值是否相等,将不相等的删除)。

最后,得到两条符合条件的数据。

⼆、select * from A where id in(select id from B)以上查询使⽤了in语句,in()只执⾏⼀次,它查出B表中的所有id字段并缓存起来.之后,检查A表的id是否与B表中的id相等,如果相等则将A表的记录加⼊结果集中,直到遍历完A表的所有记录. 它的查询过程类似于以下过程List resultSet=[]; Array A=(select * from A); Array B=(select id from B);for(int i=0;i<A.length;i++) { for(int j=0;j<B.length;j++) { if(A[i].id==B[j].id) { resultSet.add(A[i]); break; } } } return resultSet;可以看出,当B表数据较⼤时不适合使⽤in(),因为它会B表数据全部遍历⼀次. 如:A表有10000条记录,B表有1000000条记录,那么最多有可能遍历10000*1000000次,效率很差. 再如:A表有10000条记录,B表有100条记录,那么最多有可能遍历10000*100次,遍历次数⼤⼤减少,效率⼤⼤提升.结论:in()适合B表⽐A表数据⼩的情况exists ⼀、指定⼀个⼦查询,检测⾏的存在。

子查询之exists和in

子查询之exists和in

⼦查询之exists和inexistsexists⽤于检查⼀个⼦查询是否⾄少会返回⼀⾏数据(即检测⾏的存在),返回值为boolean型,true或false语法exists subquery/*参数:subquery是⼀个受限的select语句(不允许有compute⼦句和into关键字),该语句返回⼀个结果集。

返回结果类型:boolean类型如果⼦查询包含⾏,则返回true,否则返回false,即⾔:exists根据subquery的结果集是否为空来返回⼀个布尔值——如果不为空则返回true,否则返回false*/table1 table2id class_name id name class_id01 ⼀年级 01 张三 0102 ⼆年级 02 李四 0203 三年级 04 王五 04-- 1、在⼦查询中使⽤NULL仍然返回结果集:select * from table1 where exists(select null)-- 该条sql语句等同于:select * from table1其查询结果为:id class_name01 ⼀年级02 ⼆年级03 三年级-- 2、select t1.id,t1.class_name from table1 t1 where exists (select * from table2 t2 where t2.class_id = t1.id)-- 该条sql语句等同于:select t1.id,t1.class_name from table1 t1 where t1.id in (select t2.class_id from table2 t2 where t2.class_id = t1.id)其查询的结果为:id class_name01 ⼀年级02 ⼆年级select t1.id,t1.class_name from table1 t1 where exists (select * from table2 t2 where t2.class_id = '01')-- 等价于select * from table2 t2 where t2.class_id = '01'有数据存在,所以exists返回true;select t1.id,t1.class_name from table1 t1 where exists (select * from table2 t2 where t2.class_id = '02')-- 等价于 select * from table2 t2 where t2.class_id = '02'有数据存在,所以exists返回true;select t1.id,t1.class_name from table1 t1 where exists (select * from table2 t2 where t2.class_id = '03')-- 等价于 select * from table2 t2 where t2.class_id = '03'没有数据存在,所以exists返回false;执⾏过程理解:将外查询表的每⼀⾏,代⼊内查询作为检验,如果内查询返回的结果取⾮空值,即exists⼦句返回true,则外查询的这⼀⾏可作为外查询的结果⾏,否则不能作为结果。

MySQLIN和EXISTS的效率问题,以及执行优化

MySQLIN和EXISTS的效率问题,以及执行优化

MySQLIN和EXISTS的效率问题,以及执⾏优化⽹上可以查到很多这样的说法:如果查询的两个表⼤⼩相当,那么⽤in和exists差别不⼤。

如果两个表中⼀个较⼩,⼀个是⼤表,则⼦查询表⼤的⽤exists,⼦查询表⼩的⽤in:例如:表A(⼩表),表B(⼤表)1:select * from A where cc in (select cc from B) 效率低,⽤到了A表上cc列的索引;select * from A where exists(select cc from B where cc=) 效率⾼,⽤到了B表上cc列的索引。

相反的2:select * from B where cc in (select cc from A) 效率⾼,⽤到了B表上cc列的索引;select * from B where exists(select cc from A where cc=) 效率低,⽤到了A表上cc列的索引。

将下⾯的语句执⾏优化:select count(uid) from user where uid in (SELECT did FROM demo);select count(uid) from user where exists (SELECT 1 FROM demowhere demo.did = user.uid);1.注意慢的原因就是内部每次与外部⽐较时,都需要遍历⼀次表操作,可以采⽤另外⼀个⽅法,在嵌套⼀层⼦查询,避免多次遍历操作SELECT count(did) FROM demo where exists (SELECT uid FROM (SELECT uid from user) as b where b.uid = demo.did);2.第⼆种优化就是先将⼦查询⾥的语句执⾏,使⽤GROUP_CONCAT将字段连接起来,如果字符串长度不够可以使⽤:SET SESSION group_concat_max_len = 102400;原sql:SELECTc.idFROMc 此表有712995条数据LEFT JOIN u ON er_id = u.idLEFT JOIN doc ON c.doctor_id = doc.idLEFT JOIN s ON c.meal_id = s.idWHEREs.renew = 1AND c.orderstatus = 1AND c.endtime < UNIX_TIMESTAMP()AND _type = 'c'AND u.is_doctor = 0AND u.active = 1AND doc.is_doctor IN (4, 5)AND doc.is_family_doctor = 1AND doc.active = 1AND er_id NOT IN (SELECTuser_idFROMd 此表有934455条数据WHEREd.log LIKE '%结束');-- 执⾏时间为2.265s优化后:SET SESSION group_concat_max_len = 102400;SELECT GROUP_CONCAT(user_id) FROM d WHERE d.log LIKE '%结束'; -- 执⾏了0.521sSELECTc.idFROMcLEFT JOIN u ON er_id = u.idLEFT JOIN doc ON c.doctor_id = doc.idLEFT JOIN s ON c.meal_id = s.idWHEREs.renew = 1AND c.orderstatus = 1AND c.endtime < UNIX_TIMESTAMP()AND _type = 'c'AND u.is_d = 0AND u.active = 1AND doc.is_d IN (4, 5)AND doc.is_f_d = 1AND doc.active = 1AND er_id NOT IN (24986,24986,24986,24986,24986,24986,..............................................⼤概5千个id);-- 执⾏时间1.579s执⾏时间少了0.686s,但是GROUP_CONCAT(user_id)还执⾏了0.521s,所以总体时间没有什么差别(当前数量级),⽽且后⼀个需要考虑字符串的⼤⼩问题。

Oracle中in与exist,not in与not exist的性能问题

Oracle中in与exist,not in与not exist的性能问题

上星期五与haier讨论in跟exists的性能问题,正好想起原来公司的一个关于not in的规定,本想做个实验证明我的观点是正确的,但多次实验结果却给了我一个比较大的教训。

我又咨询了下oracle公司工作的朋友,确实是我持有的观点太保守了。

于是写个文章总结下,希望对大家有所启发。

后面可能有大篇是关于10053 trace的内容,只作实验证明,可直接忽略看最终的结论即可。

我们知道,in 是把外表和内表作hash 连接,而exists是对外表作loop循环,每次loop循环再对内表进行查询。

一直以来认为exists比in效率高的说法是不准确的。

如果查询的两个表大小相当,那么用in和exists是差别不大的。

但如果两个表中一个较小,一个是大表,则子查询表大的用exists,子查询表小的用in,效率才是最高的。

假定表A(小表),表B(大表),cc列上都有索引:•select * from A where cc in(select ccfrom B); --效率低,用到了A表上cc列的索引•select * from A where exists(select cc from B where cc=A.cc); --效率高,用到了B 表上cc列的索引。

相反的:•select * from B where cc in (select cc from A); --效率高,用到了B表上cc列的索引•select * from B where exists(select ccfromA where cc=); --效率低,用到了A表上cc列的索引通过使用exists,Oracle会首先检查主查询,然后运行子查询直到它找到第一个匹配项,这就节省了时间。

Oracle在执行IN子查询时,首先执行子查询,并将获得的结果列表存放在一个加了索引的临时表中。

在执行子查询之前,系统先将主查询挂起,待子查询执行完毕,存放在临时表中以后再执行主查询。

MySQL中in与exists的使用及区别介绍

MySQL中in与exists的使用及区别介绍

MySQL中in与exists的使⽤及区别介绍先放⼀段代码for(int i=0;i<1000;i++){for(int j=0;j<5;j++){System.out.println("hello");}}for(int i=0;i<5;i++){for(int j=0;j<1000;j++){System.out.println("hello");}}分析以上代码可以看到两⾏代码除了循环的次序不⼀致意外,其他并⽆区别,在实际执⾏时两者所消耗的时间和空间应该也是⼀致的。

但是这仅仅是在Java中,现在我们转化⼀下情景,最外层循环是数据库中的连接操作,内层循环为查找操作,那么现在两次的结果将相差巨⼤。

之所以出现这样的原因是数据库的特点决定的,数据库中相⽐较于查询操作⽽⾔,建⽴连接是更消耗资源的。

第⼀段代码建⽴了1000次连接,每⼀次连接却只做了5次查询,显然是很浪费的。

因此在我们对数据库进⾏操作时需要遵循的操作应当是⼩表驱动⼤表(⼩的数据集驱动⼤的数据集)。

in与exists表结构tbl_emp为员⼯表,deptld为部门id。

tbl_dept为部门表。

员⼯表中含有客⼈,其deptld字段为-1mysql> desc tbl_emp;+--------+-------------+------+-----+---------+----------------+| Field | Type | Null | Key | Default | Extra |+--------+-------------+------+-----+---------+----------------+| id | int(11) | NO | PRI | NULL | auto_increment || name | varchar(20) | YES | | NULL | || deptld | int(11) | YES | MUL | NULL | |+--------+-------------+------+-----+---------+----------------+3 rows in set (0.00 sec)mysql> desc tbl_dept;+----------+-------------+------+-----+---------+----------------+| Field | Type | Null | Key | Default | Extra |+----------+-------------+------+-----+---------+----------------+| id | int(11) | NO | PRI | NULL | auto_increment || deptName | varchar(30) | YES | MUL | NULL | || locAdd | varchar(40) | YES | | NULL | |+----------+-------------+------+-----+---------+----------------+3 rows in set (0.01 sec)我们知道对于⼀个公司⽽⾔相对于部门来说员⼯数要多得多。

in的对象选择(子查询还是List集合),in的优化,in与exists

in的对象选择(子查询还是List集合),in的优化,in与exists

in的对象选择(⼦查询还是List集合),in的优化,in与exists 近⽇查看SQL慢查询⽇志,发现对于in的查询总是出现超时问题。

超时相关SQL语句:select * from flow_ru_bizvar where businessId IN () and status = 0。

可以看到在这句SQL中,最耗时的就是因为in的原因。

这⾥in的对象是⼀个Long类型(businessId)的List。

先是从另⼀个表中,select出相关的businessId,然后再根据这些businessId进⾏查询。

这样做的⽬的是为了避免表链接⽽带来的耗时,然⽽,从结果来看这样的处理结果还是耗时的。

所以,关于这两个种⽅式究竟那种较好,以及各⾃的使⽤条件,如何对其两种进⾏优化。

1.当是集合时,in的处理机制:2.当是⼦查询时,in的处理机制:⾸先执⾏⼦查询,其查询出来的结果作为衍⽣表(临时表),同时,其原有的索引仍然会起作⽤。

3.in与exists的区别以及使⽤条件exists使⽤主查询中的表作为驱动表,适⽤于⼦查询中的表有索引⽀持,主查询中的表数据较少时的情况。

exists 对主表进⾏loop,根据主表的值去查看⼦表的结果(⼦表的结果为true或false),若⼦表的结果为true,则返回主表的结果,否则不返回主表的结果。

in使⽤⼦查询中的表作为驱动表,适⽤于主查询中的表有索引⽀持,⼦查询中的表数据较少时的情况。

其执⾏流程,将主查询的结果集与⼦查询的结果集进⾏内链接。

测试语句:explain select *from flow_ru_businesswhere flow_ru_business.businessId in (select gte_order.businessId from gte_order where gte_order.status = 7);主查询使⽤遍历全表⽽不是遍历索引的原因是:主查询要求返回出所有元素字段,只能查表,如果满⾜覆盖索引才会遍历索引⽽不是表。

in和extexs

in和extexs

in和exists的区别与SQL执行效率in和exists的区别与SQL执行效率最近很多论坛又开始讨论in和exists的区别与SQL执行效率的问题,本文特整理一些in和exists的区别与SQL执行效率分析SQL中in可以分为三类:1、形如select * from t1 where f1 in ('a','b'),应该和以下两种比较效率select * from t1 where f1='a' or f1='b'或者select * from t1 where f1 ='a' union all select * from t1 f1='b'你可能指的不是这一类,这里不做讨论。

2、形如select * from t1 where f1 in (select f1 from t2 where t2.fx='x'),其中子查询的where里的条件不受外层查询的影响,这类查询一般情况下,自动优化会转成exist语句,也就是效率和exist一样。

3、形如select * from t1 where f1 in (select f1 from t2 where t2.fx=t1.fx),其中子查询的where里的条件受外层查询的影响,这类查询的效率要看相关条件涉及的字段的索引情况和数据量多少,一般认为效率不如exists。

除了第一类in语句都是可以转化成exists 语句的SQL,一般编程习惯应该是用exi sts而不用in,而很少去考虑in和exists的执行效率.in和exists的SQL执行效率分析A,B两个表,(1)当只显示一个表的数据如A,关系条件只一个如ID时,使用IN更快:select * from A where id in (select id from B)(2)当只显示一个表的数据如A,关系条件不只一个如ID,col1时,使用IN就不方便了,可以使用EXISTS:select * from Awhere exists (select 1 from B where id = A.id and col1 = A.col1)(3)当只显示两个表的数据时,使用IN,EXISTS都不合适,要使用连接:select * from A left join B on id = A.id所以使用何种方式,要根据要求来定。

数据库查询exists的用法

数据库查询exists的用法

数据库查询exists的用法数据库查询exists的用法的用法你知道吗?下面小编就跟你们详细介绍下数据库查询exists的用法的用法,希望对你们有用。

数据库查询exists的用法的用法如下:有一个查询如下:复制代码代码如下:SELECT c.CustomerId, CompanyNameFROM Customers cWHERE EXISTS(SELECT OrderID FROM Orders oWHERE o.CustomerID = cu.CustomerID)这里面的EXISTS是如何运作呢?子查询返回的是OrderId字段,可是外面的查询要找的是CustomerID和CompanyName字段,这两个字段肯定不在OrderID里面啊,这是如何匹配的呢?EXISTS用于检查子查询是否至少会返回一行数据,该子查询实际上并不返回任何数据,而是返回值True或False。

EXISTS 指定一个子查询,检测行的存在。

语法:EXISTS subquery。

参数subquery 是一个受限的SELECT 语句(不允许有COMPUTE 子句和 INTO 关键字)。

结果类型为 Boolean,如果子查询包含行,则返回 TRUE。

在子查询中使用 NULL 仍然返回结果集这个例子在子查询中指定NULL,并返回结果集,通过使用EXISTS 仍取值为 TRUE。

复制代码代码如下:SELECT CategoryNameFROM CategoriesWHERE EXISTS (SELECT NULL)ORDER BY CategoryName ASC比较使用 EXISTS 和 IN 的查询这个例子比较了两个语义类似的查询。

第一个查询使用 EXISTS 而第二个查询使用 IN。

注意两个查询返回相同的信息。

复制代码代码如下:SELECT DISTINCT pub_nameFROM publishersWHERE EXISTS(SELECT *FROM titlesWHERE pub_id = publishers.pub_idAND type = \'business\')复制代码代码如下:SELECT distinct pub_nameFROM publishersWHERE pub_id IN(SELECT pub_idFROM titlesWHERE type = \'business\')比较使用 EXISTS 和 = ANY 的查询本示例显示查找与出版商住在同一城市中的作者的两种查询方法:第一种方法使用 = ANY,第二种方法使用 EXISTS。

Mysql之IN和Exists用法

Mysql之IN和Exists用法

Mysql之IN和Exists⽤法1.基本⽤法 IN:后⾯的⼦查询是返回结果集的,换句话说执⾏次序和Exists()不⼀样.⼦查询先产⽣结果集,然后主查询再去结果集⾥去找符合要求的字段列表去.符合要求的输出,反之则不输出.Exists:后⾯的⼦查询被称做相关⼦查询, 他是不返回列表的值的.只是返回⼀个ture或false的结果(这也是为什么⼦查询⾥是 "select 1 "的原因,当然也可以select任何东西) 其运⾏⽅式是先运⾏主查询⼀次。

再去⼦查询⾥查询与其对应的结果,如果是ture则输出,反之则不输出.再根据主查询中的每⼀⾏去⼦查询⾥去查询。

2.运⾏过程Exists执⾏顺序如下: 1.⾸先执⾏⼀次外部查询 2.对于外部查询中的每⼀⾏分别执⾏⼀次⼦查询,⽽且每次执⾏⼦查询时都会引⽤外部查询中当前⾏的值。

3.使⽤⼦查询的结果来确定外部查询的结果集。

(如果外部查询返回100⾏,SQL 就将执⾏101次查询,⼀次执⾏外部查询,然后为外部查询返回的每⼀⾏执⾏⼀次⼦查询。

但实际上,SQL的查询优化器有可能会找到⼀种更好的⽅法来执⾏相关⼦查询,⽽不需要实际执⾏101次查询。

)IN的执⾏过程如下: 1.⾸先运⾏⼦查询,获取⼦结果集 2.主查询再去结果集⾥去找符合要求的字段列表,.符合要求的输出,反之则不输出。

3.区别3.1 IN和ExistsIN是把外表和内表作hash 连接,⽽Exists是对外表作loop循环,每次loop循环再对内表进⾏查询。

⼀直以来认为Exists⽐IN效率⾼的说法是不准确的。

如果查询的两个表⼤⼩相当,那么⽤IN和Exists差别不⼤。

如果两个表中⼀个较⼩,⼀个是⼤表,则⼦查询表⼤的⽤Exists,⼦查询表⼩的⽤IN:例如:表A(⼩表),表B(⼤表): select* from A where cc in(select cc from B)效率低,⽤到了A表上cc列的索引; select* from A where exists(select cc from B where cc=)效率⾼,⽤到了B表上cc列的索引。

Oracle中in与exist,notin与notexist性能问题

Oracle中in与exist,notin与notexist性能问题

上星期五与haier讨论in跟exists的性能问题,正好想起原来公司的一个关于not in的规定,本想做个实验证明我的观点是正确的,但多次实验结果却给了我一个比较大的教训。

我又咨询了下oracle公司工作的朋友,确实是我持有的观点太保守了。

于是写个文章总结下,希望对大家有所启发。

后面可能有大篇是关于10053 trace的内容,只作实验证明,可直接忽略看最终的结论即可。

我们知道,in 是把外表和内表作hash 连接,而exists是对外表作loop循环,每次loop循环再对内表进行查询。

一直以来认为exists比in效率高的说法是不准确的。

如果查询的两个表大小相当,那么用in和exists是差别不大的。

但如果两个表中一个较小,一个是大表,则子查询表大的用exists,子查询表小的用in,效率才是最高的。

假定表A(小表),表B(大表),cc列上都有索引:•select * from A where cc in (select cc from B)。

--效率低,用到了A表上cc列的索引•select * from A where exists(select cc from B where cc=)。

--效率高,用到了B表上cc 列的索引。

相反的:•select * from B where cc in (select cc from A)。

--效率高,用到了B表上cc列的索引•select * from B where exists(select cc from A where cc=)。

--效率低,用到了A表上cc 列的索引通过使用exists,Oracle会首先检查主查询,然后运行子查询直到它找到第一个匹配项,这就节省了时间。

Oracle在执行IN子查询时,首先执行子查询,并将获得的结果列表存放在一个加了索引的临时表中。

在执行子查询之前,系统先将主查询挂起,待子查询执行完毕,存放在临时表中以后再执行主查询。

oracle中代替in的用法

oracle中代替in的用法

oracle中代替in的用法摘要:1.Oracle 中IN 的用法简介2.Oracle 中替代IN 的其他用法a.使用EXISTS 代替INb.使用JOIN 代替INc.使用NOT IN 的替代用法3.总结和展望正文:Oracle 中IN 的用法简介在Oracle 数据库中,IN 操作符用于在一个查询中测试一个列的值是否在另一个列的值列表中。

这种操作符在SQL 查询中非常常见,可以大大简化查询语句。

然而,有时候,IN 操作符的使用可能会导致查询效率低下,尤其是在查询条件较多时。

在这种情况下,了解一些替代IN 的用法就显得尤为重要。

Oracle 中替代IN 的其他用法a.使用EXISTS 代替INEXISTS 操作符用于测试一个查询是否至少返回一条记录。

它可以用来替代IN 操作符,尤其是当查询条件中的列是聚合函数时。

例如,假设我们有一个包含销售记录的表,我们想要查询所有销售额大于1000 的记录。

使用IN 操作符的查询语句如下:```sqlSELECT * FROM sales WHERE sales_amount > 1000;```使用EXISTS 操作符的查询语句如下:```sqlSELECT * FROM sales WHERE EXISTS (SELECT 1 FROM sales WHERE sales_amount > 1000);```b.使用JOIN 代替IN在一些情况下,使用JOIN 操作符可能会比使用IN 操作符更高效。

例如,假设我们有一个包含产品信息的表product 和另一个包含订单信息的表order,我们想要查询所有订单中包含的产品ID。

使用IN 操作符的查询语句如下:```sqlSELECT * FROM product WHERE product_id IN (SELECT product_id FROM order);```使用JOIN 操作符的查询语句如下:```sqlSELECT * FROM product JOIN order ON product.product_id = order.product_id;```c.使用NOT IN 的替代用法在某些情况下,使用NOT IN 操作符可能比使用IN 操作符更高效。

数据库in和exists的用法

数据库in和exists的用法

数据库in和exists的用法数据库in和exists的用法的用法如下:SELECT DISTINCT MD001 FROM BOMMD WHERE MD001 NOT IN (SELECT MC001 FROM BOMMC)NOT EXISTS,exists的用法跟in不一样,一般都需要和子表进行关联,而且关联时,需要用索引,这样就可以加快速度select DISTINCT MD001 from BOMMD WHERE NOT EXISTS (SELECT MC001 FROM BOMMC where BOMMC.MC001 = BOMMD.MD001)exists是用来判断是否存在的,当exists(查询)中的查询存在结果时则返回真,否则返回假。

not exists则相反。

exists做为where 条件时,是先对where 前的主查询询进行查询,然后用主查询的结果一个一个的代入exists的查询进行判断,如果为真则输出当前这一条主查询的结果,否则不输出。

in和existsin 是把外表和内表作hash 连接,而exists是对外表作loop循环,每次loop循环再对内表进行查询。

一直以来认为exists比in效率高的说法是不准确的。

如果查询的两个表大小相当,那么用in和exists差别不大。

如果两个表中一个较小,一个是大表,则子查询表大的用exists,子查询表小的用in:例如:表A(小表),表B(大表)1:select * from A where cc in (select cc from B)效率低,用到了A表上cc列的索引;select * from A where exists(select cc from B where cc=)效率高,用到了B 表上cc列的索引。

相反的2:select * from B where cc in (select cc from A)效率高,用到了B表上cc列的索引;select * from B where exists(select cc from A where cc=)效率低,用到了A表上cc列的索引。

数据库in和exists的用法

数据库in和exists的用法

数据库in和exists的用法数据库in和exists的用法的用法如下:SELECTDISTINCTMD001FROMBOMMDWHEREMD001NOTIN(SELECTMC001F ROMBOMMC)NOTEXISTS,exists的用法跟in不一样,一般都需要和子表进行关联,而且关联时,需要用索引,这样就可以加快速度selectDISTINCTMD001fromBOMMDWHERENOTEXISTS(SELECTMC001FR OMBOMMCwhereBOMMC.MC001=BOMMD.MD001)exists是用来判断是否存在的,当exists(查询)中的查询存在结果时则返回真,否则返回假。

notexists则相反。

exists做为where条件时,是先对where前的主查询询进行查询,然后用主查询的结果一个一个的代入exists的查询进行判断,如果为真则输出当前这一条主查询的结果,否则不输出。

in和existsin是把外表和内表作hash连接,而exists是对外表作loop循环,每次loop循环再对内表进行查询。

一直以来认为exists比in 效率高的说法是不准确的。

如果查询的两个表大小相当,那么用in和exists差别不大。

如果两个表中一个较小,一个是大表,则子查询表大的用exists,子查询表小的用in:例如:表A(小表),表B(大表)1:select*fromAwhereccin(selectccfromB)效率低,用到了A表上cc列的索引;select*fromAwhereexists(selectccfromBwherecc=)效率高,用到了B表上cc列的索引。

相反的2:select*fromBwhereccin(selectccfromA)效率高,用到了B表上cc列的索引;select*fromBwhereexists(selectccfromAwherecc=)效率低,用到了A表上cc列的索引。

exists和in的用法

exists和in的用法

"exists"和"in"在英语中常常用于不同的语境中,表达不同的含义。

以下是关于这两个词的一些基本用法和注意事项:**exists**1. **存在性**:这个词主要用于表达某个实体或概念在某个集合或范围内是存在的。

例如:“Does anyone exist in this class?”(这个班级里有人存在吗?)这里的“exist”是动词,表示“存在”。

2. **存在状态**:当我们谈论某个物体或情况的存在状态时,我们可能会使用“exists”。

例如:“My car exists in my garage.”(我的车在车库里。

)在这个句子中,“exists”表示的是一种存在状态。

**in**1. **在……里面**:这个用法主要用于表示位置或范围。

例如:“The cat is in the kitchen.”(猫在厨房里。

)在这个句子中,“in”表示的是空间位置。

2. **用某种语言或方式**:当我们在描述某种行为或情况时,我们可能会使用“in”。

例如:“She speaks French very well, in a clear and confident way.”(她法语说得非常好,用清晰而自信的方式。

)在这个句子中,“in”表示方式。

3. **在某个时间或时期**:当我们谈论某个事件或活动发生的时间或时期时,我们可能会使用“in”。

例如:“The party started in the early evening.”(晚会开始于傍晚早些时候。

)**用法建议**在使用这两个词时,建议根据语境选择合适的词。

一般来说,“exists”更常用于描述事物的存在状态,而“in”则更常用于描述空间位置、方式或时间。

同时,注意不要混淆这两个词的用法,以免产生误解。

另外,在某些情况下,你可能需要查阅相关词典或语法书籍以获取更准确和详细的解释。

这些资源通常会提供更多关于这两个词的用法、含义和例句的信息,帮助你更好地理解和使用它们。

SQL里IN的用法以及优化

SQL里IN的用法以及优化

SQL⾥IN的⽤法以及优化1.in后条件不多,可以考虑主表建索引,或⽤union all 代替2. 和 exists的区别: 如果⼦查询得出的结果集记录较少,主查询中的表较⼤且⼜有索引时应该⽤, 反之如果外层的主查询记录较少,⼦查询中的表⼤,⼜有索引时使⽤exists。

其实我们区分和exists主要是造成了驱动顺序的改变(这是性能变化的关键),如果是exists,那么以外层表为驱动表,先被访问,如果是IN,那么先执⾏⼦查询,所以我们会以驱动表的快速返回为⽬标,那么就会考虑到索引及结果集的关系了,另外IN时不对进⾏处理。

3.如果in后接⼏百⼏千或⼏万的条件,可把in⾥的条件录⼊临时表,给临时表加索引,⽤表连接代替问题描述: id值可能有数千个之多,怎么提⾼效率?例⼦:select * from table1 where id in (1,3,6,10,...,8000) and type = 1************************************************************/--例如:SELECT *FROM tbWHERE id IN (1, 2, 3, 4, ........)AND NAME = 'best'--1.将括号的条件做成变量DECLARE @str VARCHAR(4000)SET @str = '1,2,3,4,5.......'--2.然后将@s拆分后插⼊临时表CREATE TABLE #t(id VARCHAR(10))DECLARE @i INTDECLARE @len INTSET @i = 1WHILE @i < LEN(@str + ',')BEGININSERT #tSELECT SUBSTRING(@str + ',', @i, CHARINDEX(',', @str + ',', @i) -@i)SET @i = CHARINDEX(',', @str + ',', @i) + 1END--3利⽤临时表和原表进⾏连接取值SELECT k.*FROM tb kINNER JOIN #t pON p.id = k.idWHERE NAME = 'best'。

Mysql中用exists代替in

Mysql中用exists代替in

Mysql中⽤exists代替inexists对外表⽤loop逐条查询,每次查询都会查看exists的条件语句,当 exists⾥的条件语句能够返回记录⾏时(⽆论记录⾏是的多少,只要能返回),条件就为真,返回当前loop到的这条记录,反之如果exists⾥的条件语句不能返回记录⾏,则当前loop到的这条记录被丢弃,exists 的条件就像⼀个bool条件,当能返回结果集则为true,不能返回结果集则为 false如下:select * from user where exists (select 1);对user表的记录逐条取出,由于⼦条件中的select 1永远能返回记录⾏,那么user表的所有记录都将被加⼊结果集,所以与 select * from user;是⼀样的⼜如下select * from user where exists (select * from user where userId = 0);可以知道对user表进⾏loop时,检查条件语句(select * from user where userId = 0),由于userId永远不为0,所以条件语句永远返回空集,条件永远为false,那么user表的所有记录都将被丢弃not exists与exists相反,也就是当exists条件有结果集返回时,loop到的记录将被丢弃,否则将loop到的记录加⼊结果集总的来说,如果A表有n条记录,那么exists查询就是将这n条记录逐条取出,然后判断n遍exists条件in查询相当于多个or条件的叠加,这个⽐较好理解,⽐如下⾯的查询select * from user where userId in (1, 2, 3);等效于select * from user where userId = 1 or userId = 2 or userId = 3;not in与in相反,如下select * from user where userId not in (1, 2, 3);等效于select * from user where userId != 1 and userId != 2 and userId != 3;总的来说,in查询就是先将⼦查询条件的记录全都查出来,假设结果集为B,共有m条记录,然后在将⼦查询条件的结果集分解成m个,再进⾏m次查询值得⼀提的是,in查询的⼦条件返回结果必须只有⼀个字段,例如select * from user where userId in (select id from B);⽽不能是select * from user where userId in (select id, age from B);⽽exists就没有这个限制下⾯来考虑exists和in的性能考虑如下SQL语句1: select * from A where exists (select * from B where B.id = A.id);2: select * from A where A.id in (select id from B);查询1.可以转化以下伪代码,便于理解for ($i = 0; $i < count(A); $i++) { $a = get_record(A, $i); #从A表逐条获取记录 if (B.id = $a[id]) #如果⼦条件成⽴ $result[] = $a;}return $result;⼤概就是这么个意思,其实可以看到,查询1主要是⽤到了B表的索引,A表如何对查询的效率影响应该不⼤假设B表的所有id为1,2,3,查询2可以转换为select * from A where A.id = 1 or A.id = 2 or A.id = 3;这个好理解了,这⾥主要是⽤到了A的索引,B表如何对查询影响不⼤下⾯再看not exists 和 not in1. select * from A where not exists (select * from B where B.id = A.id);2. select * from A where A.id not in (select id from B);看查询1,还是和上⾯⼀样,⽤了B的索引⽽对于查询2,可以转化成如下语句select * from A where A.id != 1 and A.id != 2 and A.id != 3;可以知道not in是个范围查询,这种!=的范围查询⽆法使⽤任何索引,等于说A表的每条记录,都要在B表⾥遍历⼀次,查看B表⾥是否存在这条记录故not exists⽐not in效率⾼mysql中的in语句是把外表和内表作hash 连接,⽽exists语句是对外表作loop循环,每次loop循环再对内表进⾏查询。

mysql--exists替换in

mysql--exists替换in

mysql--exists替换inexists对外表⽤loop逐条查询,每次查询都会查看exists的条件语句,当 exists⾥的条件语句能够返回记录⾏时(⽆论记录⾏是的多少,只要能返回),条件就为真,返回当前loop到的这条记录,反之如果exists⾥的条件语句不能返回记录⾏,则当前loop到的这条记录被丢弃,exists 的条件就像⼀个boolean条件,当能返回结果集则为true,不能返回结果集则为 false如下:select * from user where exists (select 1);对user表的记录逐条取出,由于⼦条件中的select 1永远能返回记录⾏,那么user表的所有记录都将被加⼊结果集,所以与 select * from user;是⼀样的⼜如下select * from user where exists (select * from user where userId = 0);可以知道对user表进⾏loop时,检查条件语句(select * from user where userId = 0),由于userId永远不为0,所以条件语句永远返回空集,条件永远为false,那么user表的所有记录都将被丢弃not exists与exists相反,也就是当exists条件有结果集返回时,loop到的记录将被丢弃,否则将loop到的记录加⼊结果集总的来说,如果A表有n条记录,那么exists查询就是将这n条记录逐条取出,然后判断n遍exists条件in查询相当于多个or条件的叠加,这个⽐较好理解,⽐如下⾯的查询select * from user where userId in (1, 2, 3);等效于select * from user where userId = 1 or userId = 2 or userId = 3;not in与in相反,如下select * from user where userId not in (1, 2, 3);等效于select * from user where userId != 1 and userId != 2 and userId != 3;总的来说,in查询就是先将⼦查询条件的记录全都查出来,假设结果集为B,共有m条记录,然后在将⼦查询条件的结果集分解成m个,再进⾏m次查询值得⼀提的是,in查询的⼦条件返回结果必须只有⼀个字段,例如select * from user where userId in (select id from B);⽽不能是select * from user where userId in (select id, age from B);⽽exists就没有这个限制下⾯来考虑exists和in的性能考虑如下SQL语句1: select * from A where exists (select * from B where B.id = A.id);2: select * from A where A.id in (select id from B);查询1.可以转化以下伪代码,便于理解for ($i = 0; $i < count(A); $i++) { $a = get_record(A, $i); #从A表逐条获取记录 if (B.id = $a[id]) #如果⼦条件成⽴ $result[] = $a;}return $result;⼤概就是这么个意思,其实可以看到,查询1主要是⽤到了B表的索引,A表如何对查询的效率影响应该不⼤假设B表的所有id为1,2,3,查询2可以转换为select * from A where A.id = 1 or A.id = 2 or A.id = 3;这个好理解了,这⾥主要是⽤到了A的索引,B表如何对查询影响不⼤下⾯再看not exists 和 not in1. select * from A where not exists (select * from B where B.id = A.id);2. select * from A where A.id not in (select id from B);看查询1,还是和上⾯⼀样,⽤了B的索引⽽对于查询2,可以转化成如下语句select * from A where A.id != 1 and A.id != 2 and A.id != 3;可以知道not in是个范围查询,这种!=的范围查询⽆法使⽤任何索引,等于说A表的每条记录,都要在B表⾥遍历⼀次,查看B表⾥是否存在这条记录故not exists⽐not in效率⾼mysql中的in语句是把外表和内表作hash 连接,⽽exists语句是对外表作loop循环,每次loop循环再对内表进⾏查询。

  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
FROM dual
WHERE not exists (select * from clients
where clients.client_id = 10345);
使用 dual 做表名可以让你在 select 语句后面直接跟上要插入字段的值,即使这些值还不存在当前表中。
系统要求进行SQL优化,对效率比较低的SQL进行优化,使其运行效率更高,其中要求对SQL中的部分in/not in修改为exists/not exists
where clients.client_id = suppliers.supplier_id);
示例一:插入单条记录
Code:
INSERT INTO clients
(client_id, client_name, client_type)
SELECT 10345, 'IBM', 'advertising'
——如果你有一定的SQL优化经验,从这句很自然的可以想到t2绝对不能是个大表,因为需要对t2进行全表的“唯一排序”,如果t2很大这个排序的性能是不可忍受的。但是t1可以很大,为什么呢?最通俗的理解就是因为t1.x=t2.y可以走索引。但这并不是一个很好的解释。试想,如果t1.x和t2.y都有索引,我们知道索引是种有序的结构,因此t1和t2之间最佳的方案是走merge join。另外,如果t2.y上有索引,对t2的排序性能也有很大提高。
修改方法如下:
in的SQL语句
SELECT id, category_id, htmlfile, title, convert(varchar(20),begintime,112) as pubtime
FROM tab_oa_pub WHERE is_check=1 and
category_id in (select id from tab_oa_pub_cate where no='1')
问题: 我创建了一个表来存放客户信息,我知道可以用 insert 语句插入信息到表中,但是怎么样才能保证不会插入重复的记录呢?
答案: 可以通过使用 EXISTS 条件句防止插入重复记录。
示例一:插入多条记录
假设有一个主键为 client_id 的 clients 表,可以使用下面的语句:
我们要根据实际的情况做相应的优化,不能绝对的说谁的效率高谁的效率低,所有的事都是相对的
select * from t1 where x in ( select y from t2 )
事实上可以理解为:
select *
from t1, ( select distinct y from t2 ) t2
where t1.x = t2.y;
order by begintime desc
修改为exists的SQL语句
SELECT id, category_id, htmlfile, title, convert(varchar(20),begintime,112) as pubtime
FROM tab_oa_pub WHERE is_check=1 and
exists (select id from tab_oa_pub_cate where tab_oa_pub.category_id=convert(int,no) and no='1')
order by begintime desc
分析一下exists真的就比in的效率高吗?
我们先讨论IN和EXISTS。
select * from t1 where exists ( select null from t2 where y Байду номын сангаас x )
可以理解为:
for x in ( select * from t1 )
loop
if ( exists ( select null from t2 where y = x.x )
then
OUTPUT THE RECORD!
end if
end loop
——这个更容易理解,t1永远是个表扫描!因此t1绝对不能是个大表,而t2可以很大,因为y=x.x可以走t2.y的索引。
综合以上对IN/EXISTS的讨论,我们可以得出一个基本通用的结论:IN适合于外表大而内表小的情况;EXISTS适合于外表小而内表大的情况。
Code:
INSERT INTO clients
(client_id, client_name, client_type)
SELECT supplier_id, supplier_name, 'advertising'
FROM suppliers
WHERE not exists (select * from clients
SQL里的EXISTS与in、not exists与not in 效率比较和使用
SQL里的EXISTS与in、not exists与not in 效率比较和使用
在 MSSQL 中,插入(insert)一条记录很简单,但是一些特殊应用,在插入记录前,需要检查这条记录是否已经存在,只有当记录不存在时才执行插入操作,本文介绍的就是这个问题的解决方案。
相关文档
最新文档