mybatis中的#号和$号的区别

转载自:http://blog.csdn.net/leo_ace/article/details/72824962

 

      使用mybatis时动态传参,我们都知道使用#{},这也是绝大多数场景用到的,

      当需要在后台拼接查询参数,放入in中,拼接的参数格式为‘p001','p002','p003'这样的,in条件的写法in (#{product})

结果就是查询不到数据,但是把sql和参数拿到plsql中却完全没问题。

      后来突然想到$符号,后来将$符号代替#号就OK了。

 

问题原因:

#{} 默认会用引号将参数引起来

${} 单纯替代。

之前的写法,select * from product_tree_v pv where pv.product_code in(#{product})

预编译出来的结果:select * from product_tree_v pv where pv.product_code in ?;

#{}被当作一个占位符了,而参数前后也会被加上引号。

运行时的sql是:select * from product_tree_v pv where pv.product_code in('‘p001','p002','p003'');

所以无论如何都是查不到数据的。

换成${}:select * from product_tree_v pv where pv.product_code in($product});

预编译出来的结果 :select * from product_tree_v pv where pv.product_code in (‘p001','p002','p003');

这样就是纯粹的将参数传进去,没有做任何的转义操作。这才是我们真正想要的。

 

总结:

mybatis作为ORM框架,从性能,系统维护性,实用性上来说,都是非常优秀的,

其所有的sql在执行前都会通过数据库驱动进行预编译,这样DBMS就可以不用编译直接接收参数运行,

而#和$号的区别在预编译后就能看出来了,#{}预编译完是占位符?,而${}预编译完就是传进来的参数。

 

#{}的优点:

  使用#{}可以预防sql攻击,而${}却不能

例如 select * from ${tablename}   如果传入的是 product; drop product;

那么你的表数据就会被无声无息的干掉了。

使用${}的场景:

1 作为in条件时,

        2 参数为int类型并且数据库中字段的类型是number,

        3 表名

        4 order by ${},排序字段

 

--------ps---------

的用法,在该符号内的语句,将不会被当成字符串来处理,而是直接当成sql语句,比如有大于,小于号,要执行一个存储过程

都需要加上这个。

 

你可能感兴趣的:(MyBatis)