SQL,exists和in的区别

2022-10-02 13:15:39

exists 和 in 的区别:
如果子查询得出的结果集记录较少,主查询中的表较大且有索引时应该用in,
反之如果外层的主查询记录较少,子查询中的表大,有索引时使用exists。
其实区分exists和in主要是造成了驱动顺序的改变(这是性能变化的关键),如果是exists,那么以外层表为驱动表,先被访问,如果是in,那么先执行子查询,所以我们会以驱动表的快速返回为目标,那么就会考虑到索引及结果集的关系了,另外IN时不对NULL进行处理。
exists是对外表作loop循环,每次loop循环再对内表进行查询,而in 是把外表和内表作hash 连接。所以exists比in效率高的说法是不准确的。
not exists 和 not in:
如果查询语句使用了not in 那么内外表都进行全表扫描,没有用到索引;而not extsts 的子查询依然能用到表上的索引。所以无论哪个表大,用not exists都比not in要快。

对exists和in分析如下

现有两张表user表和order表:
在这里插入图片描述
在这里插入图片描述

exists

指定一个子查询,检测行的存在。遍历循环外表,然后看外表中的记录有没有和内表的数据一样的。匹配上就将结果放入结果集中。
具体sql语句如下:

SELECT  user.* FROM user
WHERE
EXISTS (
	SELECT order.user_id FROM order
	WHERE
	user.id = order.user_id
)

执行结果如下:
在这里插入图片描述
执行顺序:
使用exists关键字进行查询的时候,首先查询的是主查询的表,也就是说,我们先执行的sql语句是:
select user.* from user
在这里插入图片描述
然后,根据表的每一条记录,执行以下语句,依次去判断where后面的条件是否成立:
EXISTS (
SELECT order.user_id FROM order
WHERE
user.id = order.user_id
)
如果成立则返回true不成立则返回false。如果返回的是true的话,则该行结果保留,如果返回的是false的话,则删除该行,最后将得到的结果返回。

in

确定给定的值是否与子查询或列表中的值相匹配。in在查询的时候,首先查询子查询的表,然后将内表和外表做一个笛卡尔积,然后按照条件进行筛选。所以相对内表比较小的时候,in的速度较快。
具体sql语句如下:

SELECT  *  FROM user
WHERE
user.id IN (
	SELECT order.user_id FROM order
)

通过子查询查到的user_id 的数据,去匹配user表中的id然后得到结果:
在这里插入图片描述
执行顺序:
首先,在数据库内部,查询子查询,执行如下代码:
SELECT order.user_id FROM order
得到结果如下:
在这里插入图片描述
再将查询到的结果和原有的user表做一个笛卡尔积,结果如下:
在这里插入图片描述
再根据 ‘user’.id IN order.user_id的条件,将结果进行筛选(既比较id列和user_id 列的值是否相等,将不相等的删除)。最后,得到两条符合条件的数据:
在这里插入图片描述

  • 作者:Ayla56
  • 原文链接:https://blog.csdn.net/DxhToStage/article/details/86985897
    更新时间:2022-10-02 13:15:39