动态 SQL 是 MyBatis 的强大特性之一。如果你使用过 JDBC 或其它类似的框架,你应该能理解根据不同条件拼接 SQL 语句有多痛苦,例如拼接时要确保不能忘记添加必要的空格,还要注意去掉列表最后一个列名的逗号,还有臭名昭著苏的SQL拼接问题。利用动态 SQL,可以彻底摆脱这种痛苦。
动态SQL标签及属性列表:
where:
where标签解决了我们在之前SQL拼接问题中当传参为空时会出现“WHERE AND”情况,我们在传统的jdbc写法中为了解决这个问题,将“WHERE”改为了“WHERE 1=1”.使用where标签我们就再也不用遇到这种情况,where标签会自动检测如果它包含的标签中有返回值的话,它会自动插入where,再也不用我们去手动添加. 此外如果它包含的标签中返回内容为 AND 或者 OR 开头,则它会自动替换掉,十分方便.<select id="findStudentList2" resultType="com.ffyc.mybatisdemo.model.Student" parameterType="Student"> select * from student <where> <if test="no!=null&no!=''"> no = #{no} </if> <if test="name!=null&name!=''"> name = #{name} </if> </where> </select>
if:
if标签通常用于WHERE语句,UPDATE语句,INSERT语句中,通过判断参数值来决定是否使用某个查询条件,判断是否更新某一个字段,判断是否插入某一个字段的值foreach:
foreach标签主要用于构建in条件,可在SQL中对集合进行迭代.也常用到批量删除,添加操作中.<select id="findStudentlist1" resultType="com.ffyc.mybatisdemo.model.Student"> select * from student where no in <foreach collection="list" item="no" open="(" separator="," close=")"> #{no} </foreach> </select>
trim:
格式化输出,也可用来设定或忽略前后缀<select id="findStudentList2" resultType="com.ffyc.mybatisdemo.model.Student" parameterType="Student"> select * from student <trim prefix="where" prefixOverrides="and|or"> <if test="no!=null&no!=''"> no = #{no} </if> <if test="name!=null&name!=''"> name = #{name} </if> </trim> </select>
collection:
collection属性的值有三个分别为: list,array,map 对应的参数类型分别为: LIst,数组,map集合item: 表示在迭代过程中每一个元素的别名
open: 前缀
close: 后缀
separator: 分隔符,表示迭代时每个元素之间以什么分隔
<select id="findStudentlist1" resultType="com.ffyc.mybatisdemo.model.Student"> select * from student where no in <foreach collection="list" item="no" open="(" separator="," close=")"> #{no} </foreach> </select>
choose:
从多个选项中选择一个.按照顺序判断when中的条件是否成立,有一个成立则choose结束.当choose中所有的when都不成立时,则执行otherwise中的SQL.类似于java中的switch case default.<select id="findStudentList2" resultType="com.ffyc.mybatisdemo.model.Student" parameterType="Student"> select * from student <trim prefix="where" prefixOverrides="and|or"> <choose> <when test="no!=null&no!=''"> no = #{no} </when> <otherwise> name = #{name} </otherwise> </choose> </trim> </select>
set:
没有if标签时,如果有一个参数为null,都会导致错误.当在update语句中使用if标签时,如果最后面的if没有执行,则会导致逗号多余的错误.使用SET标签可以动态的配置set关键字,和剔除追加到条件末尾的任何不相关的逗号.<update id="updateStudent" parameterType="Student"> update student <set> <if test="name!=null"> name = #{name}, </if> <if test="gender!=null"> gender = #{gender}, </if> <if test="no!=null"> no = #{no} </if> </set> where id = #{id} </update>
我们在上述标签介绍时在xml文件中示例了每个标签及属性的使用方法,因此在此处我们只示例一个简单查询列表的测试方法:
1.接口中的方法:
//动态SQl
List<Student> findStudentList2(Student student);
2.mapper.xml文件:
<select id="findStudentList2" resultType="com.ffyc.mybatisdemo.model.Student" parameterType="Student">
select * from student
<where>
<if test="no!=null&no!=''">
no = #{no}
</if>
<if test="name!=null&name!=''">
name = #{name}
</if>
</where>
</select>
3.测试类:
@Test
//动态SQL
public void findStudentlist2() {
SqlSession sqlSession = MybatisUtil.getSqlSession();
StudentDao2 studentDao2 = sqlSession.getMapper(StudentDao2.class);
Student student = new Student();
student.setNo(103); //此处我们动态传入no值进行查询
List<Student> students = studentDao2.findStudentList2(student);
System.out.println(students);
sqlSession.close();
}
4.运行结果: