一、背景介绍
mybatis框架是一个持久层框架,是Apache下的顶级项目。mybatis可以让开发者的主要精力放在sql上,通过mybatis提供的映射方式,自由灵活的生成满足需要的sql语句。MyBatis可以将向preparedStatement中的输入参数自动进行输入映射,将查询结果集灵活映射成java对象(输出映射)。
二、知识剖析
动态SQL是MyBatis最强大的特性之一。用于实现动态SQL的主要元素如下:
1、if
if标签一般用于非空验证 ,若符合 <if>标签中的条件,则在SQL语句上添加<if></if>内的条件
2、choose(when、otherwise)
choose标签是按顺序判断其内部when标签中的test条件出否成立,如果有一个成立,则 choose 结束。当 choose 中所有 when 的条件都不满则时,则执行 otherwise 中的sql。类似于Java 的 switch 语句,choose 为 switch,when 为 case,otherwise 则为 default。
3、trim(where、set)
trim是更灵活的去处多余关键字的标签,他可以实践where和set的效果。trim 元素的主要功能是可以在自己包含的内容前加上某些前缀,也可以在其后加上某些后缀,与之对应的属性是 prefix 和 suffix;可以把包含内容的首部某些内容覆盖,即忽略,也可以把尾部的某些内容覆盖,对应的属性是 prefixOverrides 和 suffixOverrides;正因为 trim 有这样的功能,所以我们也可以非常简单的利用 trim 来代替 where 元素的功能。
4、foreach
遍历collection中的集合或数组的元素,执行对应的sql语句。
三、编码实战
<!--动态查询sql-->
<select id="getWorkerList_whereIf" parameterType="Worker" resultMap="WorkerMap">
select * from Worker
<where>
<if test="id!=null and id!=''">and id_=#{id}</if>
<if test="name!=null and name!=''">and name_ like "%"#{name}"%"</if>
<if test="sex!=null and sex!=''">and sex_=#{sex}</if>
<if test="job!=null and job!=''">and job_=#{job}</if>
<if test="hobby!=null and hobby!=''">and hobby_=#{hobby}</if>
</where>
<!--foreach 查询-->
<select id="getWorkerList_foreach" parameterType="WorkerVo" resultMap="WorkerMap">
select * from Worker
<where>
<!--<include refid="query_worker_where"></include>-->
<if test="worker!=null">
<if test="worker.name!=null and worker.name!=''">and name_=#{worker.name}</if>
</if>
<if test="list!=null">
<foreach collection="list" item="worker_id" open="AND (" close=")" separator="OR">
id_= #{worker_id}
</foreach>
</if>
</where>
</select>
<!--动态修改-->
<update id="updateWorker_if_set" parameterType="Worker">
update worker
<set>
<if test="name!=null and name!=''"> name_=#{name},</if>
<if test="job!=null and job!=''">and job_=#{job},</if>
<if test="hobby!=hobby and hobby!=''">and hobby_=#{hobby}</if>
</set>
where id_=#{id}
<!--选择性动态查询-->
<select id="getWorkerList_choose" parameterType="Worker" resultMap="WorkerMap">
select * from worker
<where>
<choose>
<when test="name!=null and name!=''">name_ like "%"#{name}"%"</when>
<when test="job!=null and job!=''">and job_ =#{job}</when>
<when test="hobby!=null and hobby!=''">and hobby_=#{hobby}</when>
<otherwise>
and id_=10
</otherwise>
</choose>
</where>
</select>
<!--动态删除-->
<delete id="dynaDeleteWorker" parameterType="java.util.List">
delete from worker where id_ in
<foreach collection="list" open="(" close=")" separator="," item="l">
#{l}
</foreach>
</delete>
四、常见问题
1.数据库与实体类字段名不统一
2.别名设置
3mybatis中sql语句的#{}占位符和${}占位符有什么区别?
五、解决办法
1.mapper.xml中添加输出映射
2.全局配置文件中对多个类分别定义别名;批量定义别名,别名为对应类名
3.${}是Properties文件中的变量占位符,它可以用于标签属性值和sql内部,属于静态文本替换,。#{}是sql的参数占位符,Mybatis会将sql中的#{}替换为?号,在sql执行前会使用PreparedStatement的参数设置方法,按序给sql的?号占位符设置参数
六、拓展思考
添加包装类的输入映射,方便拓展,无需改动原有类字段。
七、参考文献
https://blog.csdn.net/qq_32588349/article/details/51541871
https://blog.csdn.net/eson_15/article/details/51649245
https://blog.csdn.net/chenyidong521/article/details/70259806