首页 > 其他分享 >MyBatis中 # 和 $ 区别

MyBatis中 # 和 $ 区别

时间:2023-09-22 17:44:22浏览次数:34  
标签:语句 区别 sql 使用 占位 SQL MyBatis

在使用mybatis框架开发项目编写SQL语句的时候,经常需要用到变量替换值,那么用来替换变量值的操作经常用到$和#这两个符号,同样在一些Java面试中也经常被问到它们的区别。那么它们在使用上面有什么区别呢?下面根据使用情况分析总结,两者的区别。

#占位符的特点

1. MyBatis处理 #{ } 占位符,使用的 JDBC 对象是PreparedStatement 对象,执行sql语句的效率更高。

2. 使用PreparedStatement 对象,能够避免 sql 注入,使得sql语句的执行更加安全。

3. #{ } 常常作为列值使用,位于sql语句中等号的右侧;#{ } 位置的值与数据类型是相关的。

$占位符的特点 

1. MyBatis处理 ${ } 占位符,使用的 JDBC 对象是 Statement 对象,执行sql语句的效率相对于 #{ } 占位符要更低。

2. ${ } 占位符的值,使用的是字符串连接的方式,有 sql 注入的风险,同时也存在代码安全的问题。

3. ${ } 占位符中的数据是原模原样的,不会区分数据类型。

4. ${ } 占位符常用作表名或列名,这里推荐在能保证数据安全的情况下使用 ${ }。

SQL 注入

${}方式是将形参和SQL语句直接拼接形成完整的SQL命令后,再进行编译,所以可以通过精心设计的形参变量的值,来改变原SQL语句的使用意图从而产生安全隐患,即为SQL注入攻击。现举例说明:

现有Mapper映射文件如下:

 <select id="findByName" parameterType="String" resultMap="studentResultMap">
        SELECT * FROM user WHERE username='${value}'
    </select>

当 username = "' OR 1=1 OR '" 传入后,${}将变量内容直接和SQL语句进行拼接,结果如下:

SELECT * FROM user WHERE username='' OR 1=1 OR '';

显而易见,上述语句将把整个数据库内容直接暴露出来了

#{}方式则是先用占位符代替参数将SQL语句先进行预编译,然后再将参数中的内容替换进来。由于SQL语句已经被预编译过,其SQL意图将无法通过非法的参数内容实现更改,其参数中的内容,无法变为SQL命令的一部分。故,#{}可以防止SQL注入而${}却不行

 

#和$使用场景不同

(1)在sql语句中,如果要接收传递过来的变量的值的话,必须使用#。因为使用#是通过PreparedStement接口来操作,可以防止sql注入,并且在多次执行sql语句时可以提高效率。

(2)$只是简单的字符串拼接而已,所以要特别小心sql注入问题。对于sql语句中非变量部分,那就可以使用$,比如$方式一般用于传入数据库对象(如传入表名)。

例如:

select * from ${tableName},$ 对于不同的表执行统一的查询操作时,就可以使用$来完成。

(3)如果在sql语句中能同时使用#和$的时候,最好使用#。

标签:语句,区别,sql,使用,占位,SQL,MyBatis
From: https://www.cnblogs.com/zhangsai/p/17723011.html

相关文章

  • 字符'1'和整数1的区别
    字符'1'和整数1的区别━━━━━━━━━━━━━━━━━━━━━━字符'1'是一个符号,在内存中以ASCII码对应的二进制00110001存放;整数1是一个数字,在内存中以数字1的二进制的补码00000001存放。......
  • 物联网中北向接口和南向接口区别
    北向接口和南向接口的区别:功能方向:北向接口面向上层设备,提供设备管理和监控功能;南向接口面向下层设备,实现设备的配置和控制。数据传输:北向接口主要用于传输设备状态、数据上报、性能和配置信息;南向接口主要用于传输命令和配置信息。协议和命令集:北向接口通常使用标准的网络......
  • 微信小程序全局变量(globalData)和缓存(StorageSync)的区别和用法
    globalData和storage的区别一、app.globalData是全局变量,下次进入的时候,就要重新获取,一般用于:1、保存一些可能涉及安全类的数据,例如资源类,每次需要很准确的,就建议用全局变量。2、全局变量每次关闭小程序重新打开的时候,都会进行初始化更新。二、缓存(StorageSync)本地存储,storage......
  • 枚举与类的区别
    枚举的构造方法是私有的private修饰可以,public修饰报错类的构造方法是公有的public修饰2说到枚举只能私有构造,所以如果枚举类里定义抽象方法,每个实例里边都需要实现这个方法如果要实现一个接口,每个实例方法里边也要实现接口里的所有方法如果枚举类里定义了普通方法,实例是......
  • 一次性搞懂JS字符串截取方法substring()、slice()以及substr()的用法和区别
    substring()和slice()都接受两个参数,“start”和“end”。“start”表示截取的开始位置,“end”表示结束的位置(不包括该位置的字符,也就是前要后不要)。如果不传参数,则返回字符串本身的一个副本。 如果只传一个参数,则从该位置开始,截取到字符串的末尾。 如果传递两个参数,则......
  • 【Python深度学习】深度学习中框架和模型的区别
        深度学习是人工智能领域的一股强大力量,它的快速发展离不开深度学习框架和模型的进步。本文将介绍深度学习框架和模型的基本概念、它们之间的联系与区别,以及如何根据项目需求选择合适的框架和模型。一、深度学习框架        深度学习框架是进行深度学习研......
  • VUE中的data(){return}与data:{}区别
    组件是一个可复用的实例,当你引用一个组件的时候,组件里的data是一个普通的对象,所有用到这个组件的都引用的同一个data,就会造成数据污染。data:{}data:{msg:0}使用return包裹后数据中变量只在当前组件中生效,不会影响其他组件。data(){return}data(){......
  • 说说医疗虚拟仿真和虚拟现实的区别?二者哪个更好?
    随着我们在仿真教育中越来越多地使用新技术,区分虚拟模式的类型很重要。虚拟仿真是一个统称,用来概括术语来描述各种基于仿真的体验,从基于屏幕的平台到沉浸式虚拟现实。然而,各虚拟平台在保真度、沉浸感和临场感的水平上有很大差异。医疗教育中存在许多虚拟解决方案的空间,对于护理虚......
  • 20230921-python的get请求和post请求区别
    1.。get请求  2。post请求   ......
  • Java中print和println的区别
    Java中print()和println()的区别区别是print()输出完毕之后不换行,而println()输出完毕后会换行,所以println()在不输出任何东西的时候,就只输出一个换行符。示例如下:System.out.println("a");System.out.print("b");System.out.print("c");控制台输出结果:abc......