客观看待mybatis 中使用 where 1=1

本文涉及的产品
全局流量管理 GTM,标准版 1个月
公共DNS(含HTTPDNS解析),每月1000万次HTTP解析
云解析 DNS,旗舰版 1个月
简介: 客观看待mybatis 中使用 where 1=1

随便一翻,可以看到使用where 1=1 的人很多, 可能这已经是一个编码习惯了。


image.png


那么使用where 1=1 ,会怎么样么 。


首先,先辟谣。  


image.pngimage.pngimage.png

where 1=1 不会导致索引失效 !
where 1=1 不会导致索引失效 !
where 1=1 不会导致索引失效 !


客观看待 :


为什么会去写这个where 1=1 ?


WHERE 1=1



示例:


   select        from user_info    where 1=1            and TYPE = #{type}    


可能很多人看到这,已经知道,其实mybatis有where 标签是专门用于这种场景的。


而且绝大多数人都知道where标签,只是还是习惯使用 where 1=1 .


其实就是两个点 :


1. 复制粘贴,随便哪个查询都是if 标签, 复制改一改, 为了不报错,加上 where 1=1 ,完事。

2. 知道mysql 会将接收到的sql 指令做优化,这种where 1=1 是会被优化掉的,所以不影响。


不影响索引命中:


image.png


不使用 where 1=1 ,能够命中索引:


image.png使用 where 1=1 ,一样命中索引:


image.png


所以再说一次 :  where 1=1 不会导致索引失效 !


Mybatis where标签



示例:


   select        from user_info                        and TYPE = #{type}            


可以看到使用where标签的话,第一个感觉就是,代码顺畅一点,但是多了一个where标签的使用知识需要知道。


可以看到,我的示例,上面 where标签  里面 的第一个if标签里面 有写 and 。


这个是没影响的,mybatis也会帮我们做优化,第一个 and这种东西没关系的。


因为多个if标签同时存在的时候,只要保证触发了的标签  两两之间是用 and 或者 or这些连接起来就行, 第一个会自动优化掉。当然这是mybatis帮我们做的事情。


我怎么知道?看源码看的 :


mybatis where标签的源码:


image.png


可以看到代码里面 where标签 只是定义了一下 所谓的前缀list,实际上还是用的super。

继承的父类,其实就是 trim 标签。


所以我们使用where标签写的示例,也可以改成使用trim标签 :


   select        from user_info                        and TYPE = #{type}              


trim标签 ,也可以瞄一眼源码:


image.png


prefix:给trim标签内sql语句加上前缀


suffix:给trim标签内sql语句加上后缀


prefixOverrides:去除多余的前缀内容,如:prefixOverrides=“AND”,去除trim标签内sql语句多余的前缀"AND"


suffixOverrides:去除多余的后缀内容,如:suffixOverrides=",",去除trim标签内sql语句多余的后缀","


那么mybatis怎么去处理这个where标签(包括任何其他标签)的呢? 其实mybatis源码上有相关的测试函数,也可以看的是怎么给我们如何解析where标签,最后拼接成sql的。


感兴趣的可以自己看看(如果你自己有想法,其实可以自己定义自己的一套规则,反正最终是解析拼接出sql语句。):


image.png


值得思考的问题



扯远了,那么回到正题, 客观看待使用 where 1=1 .


上面列了一些where标签的源码,为什么我要列这些。


其实就是为了引出一个值得思考斟酌的问题?


使用 where 1=1 ,mysql底层会帮我们优化, 不影响索引。


使用where标签, 则需要 代码层面 帮我们解析。



那么这样来说,是不是使用where标签,其实也会存在性能问题,毕竟要走代码解析?


那么是选择在java代码应用层的解析还是选择 mysql底层的优化呢?



这个问题留给大家思考。

相关文章
|
5月前
|
SQL
条件构造器,MybatisPlus支持各种复杂的where条件,其实就是Wrapper,eq是等于的意思,相当于等于那个数值,ne就是不等于,gt大于的意思,ge大于等于,QueryWrapper是做
条件构造器,MybatisPlus支持各种复杂的where条件,其实就是Wrapper,eq是等于的意思,相当于等于那个数值,ne就是不等于,gt大于的意思,ge大于等于,QueryWrapper是做
|
3月前
|
SQL XML Java
mybatis复习03,动态SQL,if,choose,where,set,trim标签及foreach标签的用法
文章介绍了MyBatis中动态SQL的用法,包括if、choose、where、set和trim标签,以及foreach标签的详细使用。通过实际代码示例,展示了如何根据条件动态构建查询、更新和批量插入操作的SQL语句。
mybatis复习03,动态SQL,if,choose,where,set,trim标签及foreach标签的用法
|
2月前
|
SQL XML Java
Mybatis的<where>,<if>等标签用法
这篇文章详细解释了Mybatis中<where>和<if>等标签的用法,展示了如何在SQL动态构建中有效地过滤条件和处理逻辑分支。
258 1
|
5月前
|
SQL
自定义SQL,可以利用MyBatisPlus的Wrapper来构建复杂的Where条件,如何自定义SQL呢?利用MyBatisPlus的Wrapper来构建Wh,在mapper方法参数中用Param注
自定义SQL,可以利用MyBatisPlus的Wrapper来构建复杂的Where条件,如何自定义SQL呢?利用MyBatisPlus的Wrapper来构建Wh,在mapper方法参数中用Param注
|
Java 数据库连接 mybatis
mybatis的where标签
mybatis的where标签
|
SQL Java 数据库连接
61MyBatis - where、trim元素
61MyBatis - where、trim元素
50 0
|
SQL
29MyBatis - 动态SQL的 where标签
29MyBatis - 动态SQL的 where标签
51 0
|
SQL XML Java
Mybatis中$ {} 和 # {}的区别,动态SQL之if、where、set、trim、foreach标签的使用
Mybatis中$ {} 和 # {}的区别,动态SQL之if、where、set、trim、foreach标签的使用
218 0
Mybatis中$ {} 和 # {}的区别,动态SQL之if、where、set、trim、foreach标签的使用
|
SQL Java 数据库连接
MyBatis动态SQL中if、where、trim、choose、when、otherwise、foreach标签及sql标签范例
MyBatis动态SQL中if、where、trim、choose、when、otherwise、foreach标签及sql标签范例
140 0
|
SQL 测试技术
MyBatis-13MyBatis动态SQL之【where、set、trim】
MyBatis-13MyBatis动态SQL之【where、set、trim】
85 0