当前位置: 首页 > article >正文

java学习总结(五)MyBatis动态sql

一、动态Sql

通过MyBatis提供的各种标签方法实现动态拼接Sql。

这些标签类似于JSTL标签,可以写控制语句动态的拼接Sql。

二、if标签、where标签

select * form user where name like '%张%' and age=23 and gener='男';

select * form user where age=23 and gender='男';

select * form user where gender='男';

select * form user;

解决方案:

select * from user where name like '%张%' and gender='男';

select * from user where and gender='男';

思路判断这个搜索条件是不是空,不是空就把and xxx拼接上,但是where后面的第一个条件是没有and。

if(name !=空) {

and name=?

}

if(age !=空) {

and age=?

}

if(gender!=空) {

and gender=?

}

SELECT * FROM student WHERE 1=1; -- 1=1 是true

1=1是不需要加的,这里加上1=1为的就是把where第一条件条件是不需要加and的,就把第一个条件做了特殊处理,后面的条件都可以统一为都加and。

select * from user where and name like '%张%' and age=23 and gender='男';

select * from user where 1=1 and name like '%张%' and age=23 and gender='男';

select * from user where 1=1 and age=23;

select * from user where 1=1 and gener='男';

select * from user where 1=1 limit ?,?

<select id="selectByCondition" parameterType="Student" resultMap="studentMap">
    SELECT <include refid="studentColumns"/>
    FROM student
    <where>
        <if test="name!=null and name!='' ">
            AND name LIKE concat('%', #{name} ,'%')
        </if>
        <if test="age!=null">
            AND age=#{age}
        </if>
        <if test="gender!=null and gender!='' ">
            AND gender=#{gender}
        </if>
    </where>

</select>
@Test
public void testselectByCondition() throws IOException {
    SqlSession sqlSession = MyBatisUtil.getSqlSession();
    Student stu = new Student();
    stu.setName("王");
    stu.setGender("女");
    List<Student> list = sqlSession.selectList("student.selectByCondition", stu);
    for (Student student : list) {
        System.out.println(student);
    }
}

三、set标签

update(User user)

update user set name=?,age=?,gender=? where id=?;

要更新的User对象原来数据: id=1,name="张三" age=23 gender="男"

update传递过来User对象: id=1, name="张三1" age=24 gender=null

gender没有设置值,用户不想修改

update user set name="张三1",age=24 where id=1;

在更新数据有些时候希望User里面只有属性值有数据的才去做更新操作,属性没有数据的时候不做任何操作还是原来的值。

update user set name=?,age=?,gender=? where id=?;

update user set name=?,age=? where id=?;

update user set age=?,gender=? where id=?;

update user set name=? where id=?;

在根据条件拼接sql时候有一个问题,如果想统一处理,最后一个“,”处理起来麻烦。

if(name !=空) {

name=?,

}

if(age !=空) {

age=?,

}

if(gender!=空) {

gender=?,

}

<update id="updateCondition" parameterType="Student">
    UPDATE student
    <set>
        <if test="name!=null and name!=''">
            name=#{name},
        </if>
        <if test="age!=null">
            age=#{age},
        </if>
        <if test="gender!=null and gender!=''">
            gender=#{gender},
        </if>
    </set>
    WHERE id=#{id}
</update>

@Test
public void testUpdateCondition() {
    SqlSession sqlSession = MyBatisUtil.getSqlSession();
    Student student = new Student();
    student.setId(1);
    student.setName("小李1");
    student.setAge(25);
    //student.setGender("女");
    int count = sqlSession.update("student.updateCondition", student);
    System.out.println(count);
    sqlSession.commit();
}

四、foreach标签

处理数组或者集合,MyBatis使用foreach标签解析。

做一个批量删除的操作,参数可以是集合或是是数组的形式传递过来:int[] idArray = {1,2,3,4};、List idList;

public int deleteAllByArray(int[] idArray);

public int deleteAll(List idList);

delete from student where id in(23,34,5,6);

delete form user where id=1 or id=2 or id=3 or id=4;

<!-- delete from student where id in(1,2,3,4) -->
<delete id="deleteAllByArray" >
    DELETE FROM student
    WHERE id IN
    <foreach collection="array" open="(" item="id" close=")" separator=",">
        #{id}
    </foreach>
</delete>

<!--Parameter 'array' not found. Available parameters are [list]-->
<delete id="deleteAllByList" >
    DELETE FROM student
    WHERE id IN
    <foreach collection="list" open="(" item="id" close=")" separator=",">
        #{id}
    </foreach>
</delete>
@Test
public void testDeleteAllByArray() {
   int[] array = {66};
   SqlSession sqlSession = MyBatisUtil.getSqlSession();;
   int count = sqlSession.delete("student.deleteAllByArray", array);
   System.out.println("count: " + count);
   sqlSession.commit();
   sqlSession.close();
}
@Test
public void testDeleteAllByList() {
   List<Integer> list = new ArrayList<Integer>();
   list.add(68);
   list.add(69);
   SqlSession sqlSession = MyBatisUtil.getSqlSession();
   int count = sqlSession.delete("student.deleteAllByList", list);
   System.out.println("count: " + count);
   sqlSession.commit();
   sqlSession.close();
}

五、choose、when、otherwise

if----else if----else if ----else

如果用户填写了名字,这个搜索就按照名字来搜索,你即使填写了别的条件也不去拼接,

如果没有填写名字,填写了年龄,就按照年龄来搜索,

如果名字和年龄都没有填写,但是填写了性别就按照性别来查找

name、age、gender搜索时候只能按照其中一个来搜索,但是优先级name>age>gender

List selectByCondition(Student student);

<select id="selectByCondition2" parameterType="Student" resultMap="studentMap">
   SELECT <include refid="studentColumns"/>
   FROM  student
   WHERE
      <choose>
         <when test="name!=null and name!=''">
            name LIKE concat('%', #{name}, '%')
         </when>
         <when test="age!=null"> 
            age=#{age}
         </when>
         <when test="gender!=null and gender!=''">
            gender=#{gender}
         </when>
         <otherwise>
         </otherwise>
      </choose>
</select>

@Test
public void testSelectByCondition1() {
    Student student = new Student();
    //student.setName("王");
    student.setAge(23);
    student.setGender("女");
    SqlSession sqlSession = MyBatisUtil.getSqlSession();
    List<Student> list = sqlSession.selectList("student.selectByCondition2", student);
    for (Student s : list) {
        System.out.println(s);
    }
}

六、trim

MyBatis 中的 标签是一个特殊的动态 SQL 元素,它用于在动态生成 SQL 语句时自动添加或删除前后缀,以及在多个元素之间添加分隔符。这在构建包含多个可选部分的 SQL 语句时非常有用,例如在 INSERT、UPDATE 或 WHERE 子句中。

<trim prefix="" prefixOverrides="" suffix="" suffixOverrides="" ></trim>
标签提供了以下几个属性:
  1. prefix:在生成的 SQL 中添加的前缀。
  2. prefixOverrides:用于删除前缀中的特定字符。
  3. suffix:在生成的 SQL 中添加的后缀。
  4. suffixOverrides:用于删除后缀中的特定字符。与 prefixOverrides 类似,但用于删除尾随的字符。

示例 1:插入语句中的选择性字段

//insert into student(id,name,age,gender) values(1,'zhangsan',23,'男');
<insert id="addSelective" parameterType="Student">
    INSERT INTO student
    <trim prefix="(" suffix=")" suffixOverrides=",">
        <if test="id != null">id,</if>
        <if test="name != null and name != ''">name,</if>
        <if test="age != null">age,</if>
        <if test="gender != null and gender != ''">gender,</if>
    </trim>
    VALUES
    <trim prefix="(" suffix=")" suffixOverrides=",">
        <if test="id != null">#{id},</if>
        <if test="name != null and name != ''">#{name},</if>
        <if test="age != null">#{age},</if>
        <if test="gender != null and gender != ''">#{gender},</if>
    </trim>
</insert>
@Test
public void testAddSelective() {
    Student student = new Student();
    //student.setName("王");
    student.setAge(23);
    student.setGender("女");
    SqlSession sqlSession = MyBatisUtil.getSqlSession();
    int count = sqlSession.insert("student.addSelective", student);
    System.out.println("count: " + count);
    sqlSession.commit();
    sqlSession.close();
}

在这个例子中, 标签用于在字段列表和值列表中自动添加圆括号,并且通过 suffixOverrides="," 属性来删除每个元素后的逗号,以避免在 SQL 语句的末尾出现多余的逗号。

示例 2:更新语句中的选择性字段

<update id="updateSelective" parameterType="Student">
    UPDATE student
    SET
    <trim suffixOverrides=",">
        <if test="name != null and name != ''">
            name = #{name},
        </if>
        <if test="age != null">
            age = #{age},
        </if>
        <if test="gender != null and gender != ''">
            gender = #{gender},
        </if>
    </trim>
    WHERE id = #{id}
</update>
@Test
public void testUpdateSelective() {
    SqlSession sqlSession = MyBatisUtil.getSqlSession();
    Student student = new Student();
    student.setId(51);
    student.setName("小李1");
    student.setAge(25);
    //student.setGender("女");
    int count = sqlSession.update("student.updateSelective", student);
    System.out.println(count);
    sqlSession.commit();
}

在这个例子中, 标签用于在 SET 子句中自动删除最后一个逗号,以避免 SQL 语句错误

示例 3:动态 WHERE 子句

<select id="selectAll" parameterType="Student" resultType="Student">
    SELECT * FROM student
    <trim prefix="WHERE" prefixOverrides="AND">
        <if test="name != null and name != ''">
            AND name LIKE concat('%', #{name}, '%')
        </if>
        <if test="age != null">
            AND age = #{age}
        </if>
    </trim>
</select>

标签是 MyBatis 动态 SQL 的一个非常有用的工具,它可以帮助开发者编写更简洁、更灵活的 SQL 映射文件


http://www.kler.cn/a/587944.html

相关文章:

  • 让 Deepseek 写一个计算器(网页)
  • SQL Server性能分析利器:SET STATISTICS TIME ON 详解与实战案例
  • Python数据结构 ——字符串
  • Go语言os标准库
  • 中考英语之09从句
  • Dubbo 服务发现
  • 从零开始写C++3D游戏引擎(开发环境VS2022+OpenGL)之十一 从打光到材质 细嚼慢咽逐条读代码系列
  • Oracle Database 11g、12c、18c、19c、21c、22c 与 23AI 各版本差异、优缺点详解
  • 结构体定义与应用
  • C++特性——智能指针
  • 基于SpringBoot3+Druid数据库连接池与外部PostgreSQL的Kubernetes Pod YAML全解析
  • Java集合 - HashMap
  • 自动化测试脚本
  • Hive SQL 精进系列:PERCENTILE_APPROX 搞定分位数
  • 电磁兼容|RC电路
  • Hooka:多功能 Shellcode 加载器生成工具详解
  • harmonyOS NEXT开发与前端开发深度对比分析
  • 【linux篇】--linux常见指令
  • MyBatis SqlSessionFactoryBuilder 的作用是什么?
  • Android 手机启动过程