0
  • 聊天消息
  • 系统消息
  • 评论与回复
登录后你可以
  • 下载海量资料
  • 学习在线课程
  • 观看技术视频
  • 写文章/发帖/加入社区
会员中心
创作中心

完善资料让更多小伙伴认识你,还能领取20积分哦,立即完善>

3天内不再提示

为什么要尽量避免使用IN和NOT IN呢?

Android编程精选 来源:博客园 作者:博客园 2022-03-18 09:46 次阅读

  • WHY?
    • 1、效率低
    • 2、容易出现问题,或查询结果有误 (不能更严重的缺点)
  • HOW?
    • 1、用 EXISTS 或 NOT EXISTS 代替
    • 2、用JOIN 代替

WHY?

IN 和 NOT IN 是比较常用的关键字,为什么要尽量避免呢?

1、效率低

项目中遇到这么个情况:

t1表 和 t2表 都是150w条数据,600M的样子,都不算大。

但是这样一句查询 ↓

select*fromt1wherephonenotin(selectphonefromt2)

直接就把我跑傻了。。。十几分钟,检查了一下 phone在两个表都建了索引,字段类型也是一样的。原来not in 是不能命中索引的。。。。

改成 NOT EXISTS 之后查询 20s ,效率真的差好多。

select*fromt1
wherenotEXISTS(selectphonefromt2wheret1.phone=t2.phone)

2、容易出现问题,或查询结果有误 (不能更严重的缺点)

以 IN 为例。建两个表:test1 和 test2

createtabletest1(id1int)
createtabletest2(id2int)

insertintotest1(id1)values(1),(2),(3)
insertintotest2(id2)values(1),(2)

我想要查询,在test2中存在的 test1中的id 。使用IN的一般写法是:

selectid1fromtest1
whereid1in(selectid2fromtest2)

结果是:

402b60b0-9474-11ec-952b-dac502259ad0.jpg图片

OK 木有问题!

但是如果我一时手滑,写成了:

selectid1fromtest1
whereid1in(selectid1fromtest2)

不小心把id2写成id1了 ,会怎么样呢?

结果是:

404094bc-9474-11ec-952b-dac502259ad0.jpg图片

EXCUSE ME!为什么不报错?

单独查询 select id1 from test2 是一定会报错: 消息 207,级别 16,状态 1,第 11 行 列名 'id1' 无效。

然而使用了IN的子查询就是这么敷衍,直接查出 1 2 3

这仅仅是容易出错的情况,自己不写错还没啥事儿,下面来看一下 NOT IN 直接查出错误结果的情况:

给test2插入一个空值:

insertintotest2(id2)values(NULL)

我想要查询,在test2中不存在的 test1中的id 。

selectid1fromtest1
whereid1notin(selectid2fromtest2)

结果是:

4050c22e-9474-11ec-952b-dac502259ad0.jpg图片

空白!显然这个结果不是我们想要的。我们想要3。为什么会这样呢?

原因是:NULL不等于任何非空的值啊!如果id2只有1和2, 那么3<>1 且 3<>2 所以3输出了,但是 id2包含空值,那么 3也不等于NULL 所以它不会输出。

跑题一句:建表的时候最好不要允许含空值,否则问题多多。

HOW?

1、用 EXISTS 或 NOT EXISTS 代替

select*fromtest1
whereEXISTS(select*fromtest2whereid2=id1)

select*FROMtest1
whereNOTEXISTS(select*fromtest2whereid2=id1)

2、用JOIN 代替

selectid1fromtest1
INNERJOINtest2ONid2=id1

selectid1fromtest1
LEFTJOINtest2ONid2=id1
whereid2ISNULL

妥妥的没有问题了!

PS:那我们死活都不能用 IN 和 NOT IN 了么?并没有,一位大神曾经说过,如果是确定且有限的集合时,可以使用。如 IN (0,1,2)。

审核编辑 :李倩



声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉
  • 数据
    +关注

    关注

    8

    文章

    6574

    浏览量

    87955
  • Join
    +关注

    关注

    0

    文章

    9

    浏览量

    3198

原文标题:面试官:为什么要尽量避免使用 IN 和 NOT IN 呢?

文章出处:【微信号:AndroidPush,微信公众号:Android编程精选】欢迎添加关注!文章转载请注明出处。

收藏 人收藏

    评论

    相关推荐

    开关电源波纹的产生、测量及抑制

    我们最终的目的是要把输出纹波降低到可以忍受的程度,达到这个目的最根本的解决方法就是要尽量避免纹波的产生,首先要清楚开关电源纹波的种类和产生原因。
    发表于 03-29 16:12 3342次阅读

    开关电源波纹的产生、测量及抑制

    我们最终的目的是要把输出纹波降低到可以忍受的程度,达到这个目的最根本的解决方法就是要尽量避免纹波的产生,首先要清楚开关电源纹波的种类和产生原因。
    发表于 07-22 09:19 1208次阅读

    一文搞定开关电源纹波的产生、测量及抑制

    开关电源纹波不可避免,我们最终的目的是要把输出纹波降低到可以忍受的程度,达到这个目的最根本的解决方法就是要尽量避免纹波的产生,首先要清楚开关电源纹波的种类和产生原因。
    发表于 05-30 16:53 1330次阅读
    一文搞定开关电源纹波的产生、测量及抑制

    开关电源纹波的产生原因及抑制方法

    我们最终的目的是要把输出纹波降低到可以忍受的程度,达到这个目的最根本的解决方法就是要尽量避免纹波的产生,首先要清楚开关电源纹波的种类和产生原因。
    发表于 10-19 11:10 1w次阅读

    开关电源纹波的产生与抑制

    我们最终的目的是要把输出纹波降低到可以忍受的程度,达到这个目的最根本的解决方法就是要尽量避免纹波的产生,首先要清楚开关电源纹波的种类和产生原因。
    发表于 09-26 15:26 5370次阅读
    开关电源纹波的产生与抑制

    一种可以保证治愈自闭症的方案,AR的解决方案

    自闭症最大的问题是,它缺乏特效治疗,并且需要尽量避免药物治疗,故此世界各国尤其是发达国家建立了许多的孤独症特殊教育和训练课程体系。
    的头像 发表于 04-13 11:32 7641次阅读

    元器件布局的10条规则

    蛇形线是Layout中经常使用的一类走线方式。其主要目的就是为了调节延时,满足系统时序设计要求。设计者首先要有这样的认识:蛇形线会破坏信号质量,改变传输延时,布线时要尽量避免使用。但实际设计中,为了保证信号有足够的保持时间,或者减小同组信号之间的时间偏移,往往不得不故意进
    的头像 发表于 12-08 10:19 1.3w次阅读
    元器件布局的10条规则

    智能门锁爆发在即 这三道难关我们必须要小心

    “不管互联网还是传统锁具公司,惯性打法做智能门锁,只会带来恶性竞争。”智能门锁大战已经开启,在为新风口激动不已的同时,也有从业者冷眼相待。作为智能化大潮中真正的“入口级”产品,智能门锁行业要尽量避免恶性的价格战,用技术创新打造真正的智能家居入口。
    发表于 12-23 10:11 1253次阅读

    如何防止自己的无线网络被别人蹭网

    现在蹭网软件在互联网上非常多,也比较容易找到,其实路由器被蹭网,不仅仅是你网速会变慢这么简单,还可能有一些安全性的隐患,所以还是要尽量避免的。
    发表于 08-13 10:53 2159次阅读
    如何防止自己的无线网络被别人蹭网

    为什么PCB布线中要尽量避免锐角和直角走线

    如果是射频线,在转角的地方如果是直角,则有不连续性,而不连续性将易导致高次模的产生,对辐射和传导性能都有影响。RF信号线如果走直角,拐角处的有效线宽会增大,阻抗不连续,引起信号反射。为了减小不连续性,要对拐角进行处理,有两种方法:切角和圆角。圆弧角的半径应足够大,一般来说,要保证:R>3W。
    发表于 09-16 11:49 5533次阅读
    为什么PCB布线中<b class='flag-5'>要尽量</b><b class='flag-5'>避免</b>锐角和直角走线

    单片机处理ADC采样数据的方法

    单片机如何处理ADC采样数据?首先一定有小伙伴有疑问,为什么还要对采样的数据进行处理呢?直接拿来用不行吗?对于这个问题,我的回答是不建议这样做,因为任何系统都会存在干扰,不进行处理就会有数据存在一定的误差。那么我进行数据处理就是要尽量避免因外界干扰引起的误差。
    的头像 发表于 11-02 10:47 1.9w次阅读
    单片机处理ADC采样数据的方法

    PCBA免清洗工艺管理的质量要求与控制措施

    PCBA加工后免清洗是一个系统工程,从PCB设计到SMT生产过程都须严格要求,要尽量避免生产制造过程中造成人为的污染。在免清洗工艺设计和工艺管理控制上要有切实有效的措施。
    的头像 发表于 12-26 11:38 4075次阅读

    PLC应用小妙招!

    在程序中,多次调用同一个子程序,在语法方面没有什么错误,但我们要尽量避免这一做法,尤其是在带有形式参数时。下面通过一例来说明。
    发表于 07-06 09:22 144次阅读
    PLC应用小妙招!

    PCB设计布线的走线技巧

    蛇形线是Layout中经常使用的一类走线方式。其主要目的就是为了调节延时,满足系统时序设计要求。设计者首先要有这样的认识:蛇形线会破坏信号质量,改变传输延时,布线时要尽量避免使用。
    发表于 11-19 14:44 649次阅读
    PCB设计布线的走线技巧

    SMT贴片时锡膏上锡不饱满的原因有哪些?

    SMT贴片过程中,大家都知道其中一个重要环节就是焊接上锡。焊点上锡不饱满的话,对电路板的使用性能以及外形美观度都会有非常严重的影响。因此,要尽量避免锡不饱满的情况。下面就由佳金源锡膏厂家为大家详细
    的头像 发表于 11-28 16:43 417次阅读
    SMT贴片时锡膏上锡不饱满的原因有哪些?