动态语句
MyBatis动态语句是MyBatis最强大的特性之一,通过动态语句,我们可以更方便地编写SQL语句。
MyBatis中的动态语句主要包括:if、choose(when、otherwise)、trim(where、set)、foreach。
if
含义就像编程语言中的if一样,用于进行条件判断。
例如:
<select id="selectAll" parameterType="User" resultType="User">
select * from user
where gender = #{gender}
<if test="name != null and name != ''">
and name like #{name}
</if>
</select>
如果没有传入name,那么只会对gender进行匹配,否则对name也进行匹配。
choose、when、otherwise
含义就像编程语言中的switch一样,用于分支选择。
例如:
<select id="selectAll" parameterType="User" resultType="User">
select * from user
where gender = #{gender}
<choose>
<when test="name != null and name != ''">
and name like #{name}
</when>
<when test="address != null and address != ''">
and address like #{address}
</when>
<otherwise>
and locked = 0
</otherwise>
</choose>
</select>
如果没有传入name,就会检查address,如果address也没有传入,那么就会进入otherwise分支。
trim(where、set)
前面的例子中,where后面必然会跟一个条件gender = #{gender}
,但如果我们将这个条件也放入if中呢。
那么最后的sql就有可能是这样:
//所有参数为空
select * from user where
//第一个参数为空
select * from user wehre and name like 'test'
很显然上述sql语句都包含语法错误。
-
通过使用where
<select id="selectAll" parameterType="User" resultType="User"> select * from user <where> <if test="gender != null and gender != ''"> gender = #{gender} </if> <if test="name != null and name != ''"> and name like #{name} </if> </where> </select>
当where标签有返回值时,会自动在前面插入一个where,返回内容以and或or开头的话会剔除掉。这样就保证了sql语句的正确性。
-
通过使用trim
除了使用where之外,还可以使用trim
<select id="selectAll" parameterType="User" resultType="User"> select * from user <trim prefix="where" prefixOverrides="and |or "> <if test="gender != null and gender != ''"> gender = #{gender} </if> <if test="name != null and name != ''"> and name like #{name} </if> </trim> </select>
除了在where后的条件之外,还有一种类似的情况,是在update语句中的set后,只有当传入的值非空才更新。
如:
<update id="update" parameterType="User" resultType="Integer">
update user
<set>
<if test="name != null and name != ''"> name = #{name},</if>
<if test="gender != null and gender != ''"> gender = #{gender},</if>
<if test="address != null and address != ''"> address = #{address}</if>
</set>
where id = #{id}
</update>
当set标签返回值以,结尾时可以自动剔除。
除了使用set标签外,也可以使用trim
<update id="update" parameterType="User" resultType="Integer">
update user
<trim prefix="set" sufixOverrides=",">
<if test="name != null and name != ''"> name = #{name},</if>
<if test="gender != null and gender != ''"> gender = #{gender},</if>
<if test="address != null and address != ''"> address = #{address}</if>
</trim>
where id = #{id}
</update>
foreach
当传入的参数是一个集合时,我们可以通过foreach标签很方便对其进行遍历。
<select id="selectMulti" parameterType="User" resultType="User">
select * from user
where id in
<foreach item="i" index="index" collection="ids" open="(" separator="," close=")">
#{i}
</foreach>
</select>
注意:当传入参数为List时,collection的值为list,为数组时,collection的值为array,当然也可以通过在参数上加@Param("ids")注解指定名字(上述例子就是)。