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

MyBatis - 动态SQL

前言

我们在某网站填写个人信息时,时常会遇到可以选填的空(即可填,可不填),由于之前讲过的Java中的SQL语句都是固定的,且我们不可能对所有情况都写出与之对应的插入语句(太过繁琐),所以这里就引入了动态SQL。

一,<if>标签

可以通过判断当前传入的参数是否为null,来删减对应的参数。

@Mapper
public interface UserInfoXmlMapper {Integer insertUserInfo(UserInfo userInfo);
}
    <insert id="insertUserInfo" useGeneratedKeys="true" keyProperty="id">insert into userInfo(username,password,age,<if test="gender!=null">gender,</if>phone)values(#{username},#{password},#{age},<if test="gender!=null">#{gender},</if>#{phone})</insert>

二,<trim> 标签

但是如果光使用<if>标签可能会出现错误,比如:

<insert id="insertUserInfo" useGeneratedKeys="true" keyProperty="id">insert into userInfo(<if test="username!=null">username,</if><if test="password!=null">password,</if><if test="age!=null">age,</if><if test="gender!=null">gender,</if><if test="phone!=null">phone</if>)values(<if test="username!=null">#{username},</if><if test="password!=null">#{password},</if><if test="age!=null">#{age},</if><if test="gender!=null">#{gender},</if><if test="phone!=null">#{phone}</if>)</insert>

这时就要使用<trim>标签,该标签有四个属性:

  • prefix:表示整个语句块,以 prefix 的值作为前缀
  • suffix:表示整个语句块,以 suffix 的值作为后缀
  • prefixOverrides:表示整个语句块要删去的前缀
  • suffixOverrides:表示整个语句块要删去的后缀
    <insert id="insertUserInfo" useGeneratedKeys="true" keyProperty="id">insert into userInfo<trim prefixOverrides="," suffixOverrides="," prefix="(" suffix=")"><if test="username!=null">username,</if><if test="password!=null">password,</if><if test="age!=null">age,</if><if test="gender!=null">gender,</if><if test="phone!=null">phone</if></trim>values<trim prefixOverrides="," suffixOverrides="," prefix="(" suffix=")"><if test="username!=null">#{username},</if><if test="password!=null">#{password},</if><if test="age!=null">#{age},</if><if test="gender!=null">#{gender},</if><if test="phone!=null">#{phone}</if></trim></insert>

解释各个属性的作用:

  • prefix:在开始部分加上(
  • suffix:在结束部分加上 )
  • prefixOverrides:如果在所以<if>标签中内容拼接之后,以 ',' 开头,那么就将它删除
  • suffixOverrides:如果在所以<if>标签中内容拼接之后,以 ',' 结尾,那么就将它删除

后两个属性就避免出现上述SQL语句的问题

三,<where> 标签

在where条件查询中,我们的查询条件也有可能为null,所以也需要用到<if>标签,也就是说这里也会出现上述问题,只不过这里多出来的是and / or,这时就需要使用<where>标签来帮我们删除where语句开头的 and / or。注:虽然使用<trim>标签也能达到上述效果,但是如果where查询中的所有参数都为 null 时,<where>标签能将自己本身给删除,而<trim>标签仍会保留where。

    <select id="queryUserList" resultType="com.example.javaeespringioc.controller.UserInfo">select * from userInfo<where><if test="username!=null">username = #{username}</if><if test="gender!=null">and gender = #{gender}</if></where></select>

四,<set> 标签

<set>标签也是删除因<if>标签产生的多余的 ',' ,它是可以使用<trim>标签替代的

    <update id="updateUserInfo">update userInfo<set><if test="username!=null">username = #{username},</if><if test="password!=null">password = #{password}</if></set>where id = #{id}</update>

五,<foreach>标签

我们SQL中有这样的语句:delete from userinfo where id in (1,2,3,4,5),这无法使用之前的内容来表示,这时就会用到<foreach>标签,它有以下5个属性:

  • collections:绑定参数中集合,如 List,Set,Map 或 数组对象
  • item:遍历集合中的对象,类似于Java中,for(int x : nums) 中的 x
  • open:语句开头的字符串
  • close:语句结尾的字符串
  • separator:每个元素之间使用separator间隔开来
    <delete id="deleteUserInfo">delete from userInfo where id in<foreach collection="idx" item="id" separator="," open="(" close=")">#{id}</foreach></delete>

六,<include>标签

xml中的配置的SQL语句可能会存在很多重复的片段,我们可以对重复的片段进行抽取,通过<sql>标签进行封装,然后再通过<include>标签进行引用。

    <sql id="allColumn">id, username, password, age, gender, phone</sql><select id="queryUserList" resultType="com.example.javaeespringioc.controller.UserInfo">select<include refid="allColumn"></include>from userInfo<where><if test="username!=null">username = #{username}</if><if test="gender!=null">and gender = #{gender}</if></where></select>

七,<script>标签

上述6个标签都是通过.xml文件来实现动态SQL,那么我们注解如何来实现动态SQL呢?就是使用<script>标签,代码如下:

    @Select("<script>" +"select * from userInfo " +"<where>" +"<if test='username!=null'>" +"username = #{username} " +"</if>" +"<if test='gender!=null'>" +"and gender = #{gender}" +"</if>" +"</where>" +"</script>")List<UserInfo> queryBy(@Param("username") String username, @Param("gender") Integer gender);

注意:注解中的是字符串,所以要注意字符串拼接时的空格,单双引号的问题。且使用注解方式如果出错,报错信息不会告诉你哪里出问题了,所以不推荐使用该方法!!! 


http://www.mrgr.cn/news/34699.html

相关文章:

  • 对称加密与非对称加密:密码学的基石及 RSA 算法详解
  • HTML面试题(2)
  • STM32芯片EXIT外部中断的配置与原理以及模板代码(标准库)
  • Axure网络短剧APP端原型图,竖屏微剧视频模版40页
  • ChatGPT登录失败的潜在原因分析
  • 自动化运维(k8s):一键获取指定命名空间镜像包脚本
  • VirtualBox+Vagrant快速搭建Centos7系统【最新详细教程】
  • 爬虫的流程
  • 毕业设计选题:基于ssm+vue+uniapp的英语学习激励系统小程序
  • 免费的高质量、美观的甘特图模板
  • 【前端】读取 xlsx 文件并转化成 json 数据
  • Springboot Mybatis条件查询
  • 基于 Amazon Bedrock +lambda函数调用大模型构建你的智能网页助手
  • 【已解决】用JAVA代码实现递归算法-从自然数中取3个数进行组合之递归算法-用递归算法找出 n(n>=3) 个自然数中取 3 个数的组合。
  • 匈牙利算法详解与实现
  • 如何使用GLib的单向链表GSList
  • 【leetcode】环形链表、最长公共前缀
  • 注册建造师执业工程规模标准(市政公用工程)
  • 计算机毕业设计Hadoop+PySpark深圳共享单车预测系统 PyHive 共享单车数据分析可视化大屏 共享单车爬虫 共享单车数据仓库 机器学习 深度学习
  • Linux 压缩制定目录下指定类型的多个文件
  • YOLO V10简单使用
  • 0-1开发自己的obsidian plugin DAY 1
  • C++的哲学思想
  • iOS 顶级神器,巨魔录音机更新2.1正式版
  • 一看就会!PS2024下载安装教程详解
  • 在 Java 中,你如何实现不可变对象?不可变对象有哪些好处?