Mybatis中生成动态SQL的标签有四类,分别是:

  • if
  • choose (when, otherwise)
  • trim (where, set)
  • foreach

1、if

当需要动态生成where条件时,可以使用if标签:

<select id="findActiveBlogWithTitleLike"
resultType="Blog">
SELECT * FROM BLOG
WHERE state = ‘ACTIVE’
<if test="title != null and title != ''">
AND title like #{title}
</if>
</select>

当if中的条件成立时,语句块中的内容将会被加到sql中,多个查询调价可以叠加多个 if标签

2、choose, when, otherwise

当需要从多个条件中选择一项时,可以使用choose元素:

<select id="findActiveBlogLike"
resultType="Blog">
SELECT * FROM BLOG WHERE state = ‘ACTIVE’
<choose>
<when test="title != null">
AND title like #{title}
</when>
<when test="author != null and author.name != null">
AND author_name like #{author.name}
</when>
<otherwise>
AND featured = 1
</otherwise>
</choose>
</select>

choose标签只会将第一个成立的<when>标签中的语句加到sql中,如果所有的<when>都不成立,则取otherwise中的语句

3、trim, where, set

在1中的示例中,假定有where条件的情况

WHERE state = ‘ACTIVE’

如果所有where条件都需要动态生成,就需要解决一个问题:谁是第一个条件。

因为where语句中,第一个条件不需要加and(或者or),而第二个之后的条件需要and(或者or),如果你用if标签这样写:

<select id="findActiveBlogLike"
resultType="Blog">
SELECT * FROM BLOG
WHERE
<if test="state != null">
state = #{state}
</if>
<if test="title != null">
AND title like #{title}
</if>
<if test="author != null and author.name != null">
AND author_name like #{author.name}
</if>
</select>

当所有条件都不匹配时,生成的SQL是这样的:

SELECT * FROM BLOG
WHERE

或者第一个条件不成立,第二个条件成立时,生成的SQL是这样的:

SELECT * FROM BLOG
WHERE
AND title like ‘someTitle’

显然,这都是有语法错误的SQL语句。

Mybatis的Where标签可以解决这个问题

<select id="findActiveBlogLike"
resultType="Blog">
SELECT * FROM BLOG
<where>
<if test="state != null">
state = #{state}
</if>
<if test="title != null">
AND title like #{title}
</if>
<if test="author != null and author.name != null">
AND author_name like #{author.name}
</if>
</where>
</select>

<where>会自动去除多余的AND 或者OR

类似的,当update语句中set更新相关字段时,也会遇到类似的问题,生成的SQL语句可能会多或者少一个逗号。

Mybatis的<set>标签就是用来解决这个问题的:

<update id="updateAuthorIfNecessary">
update Author
<set>
<if test="username != null">username=#{username},</if>
<if test="password != null">password=#{password},</if>
<if test="email != null">email=#{email},</if>
<if test="bio != null">bio=#{bio}</if>
</set>
where id=#{id}
</update>

<set>会自动去除多余的逗号

其实,<where>和<set>,都是 通过<trim>实现的:

<trim prefix="WHERE" prefixOverrides="AND |OR ">
...
</trim>
<trim prefix="SET" suffixOverrides=",">
...
</trim>

<trim>中的<prefix>代表前缀,会插入到生成的条件前面,<prefixOverrides>代表去除前缀,<suffixOverrides>代表去除后缀,多个参数可以用管道符 "|" 分割

4、foreach

动态 SQL 的另外一个常用的操作需求是对一个集合进行遍历,通常是在构建 IN 条件语句的时候。比如:

<select id="selectPostIn" resultType="domain.blog.Post">
SELECT *
FROM POST P
WHERE ID in
<foreach item="item" index="index" collection="list"
open="(" separator="," close=")">
#{item}
</foreach>
</select>

foreach 元素的功能非常强大,它允许你指定一个集合,声明可以在元素体内使用的集合项(item)和索引(index)变量。它也允许你指定开头与结尾的字符串以及在迭代结果之间放置分隔符。这个元素是很智能的,因此它不会偶然地附加多余的分隔符。

注意 你可以将任何可迭代对象(如 List、Set 等)、Map 对象或者数组对象传递给 foreach 作为集合参数。当使用可迭代对象或者数组时,index 是当前迭代的次数,item 的值是本次迭代获取的元素。当使用 Map 对象(或者 Map.Entry 对象的集合)时,index 是键,item 是值。

[Mybatis]Mybatis 常用标签及功能整理的更多相关文章

  1. myBatis数据库常用标签

    <sql id=""></sql>:封装sql语句,被其他sql调用 <include refid=""></incl ...

  2. 最近用到mysql和mybatis结合常用的知识点坐下整理

    1.当用到集合in(x,x...)参数可以单个或者多个 ,当为单个时: findbyIds(List<Long> ids),或者findByids(Long [] ids)  <se ...

  3. [刘阳Java]_MyBatis_映射文件的常用标签总结_第5讲

    MyBatis中常用标签的总结,简单给出自己的总结 MyBatis映射文件中的标签使用介绍1.<select>:用于编写查询语句用的标签 id:表示当前<select>标签的唯 ...

  4. 【HTML】---常用标签(1)

    Html常用标签(1) 重新整理学习下前端知识从Html标签开始.我们先看HTML 骨架格式: <!DOCTYPE html> <!--这句话就是告诉我们使用哪个html版本--&g ...

  5. MyBatis - 常用标签与动态Sql

    MyBatis常用标签 ● 定义sql语句:select.insert.delete.update ● 配置JAVA对象属性与查询结构及中列明对应的关系:resultMap ● 控制动态sql拼接:i ...

  6. 9.mybatis动态SQL标签的用法

    mybatis动态SQL标签的用法   动态 SQL MyBatis 的强大特性之一便是它的动态 SQL.如果你有使用 JDBC 或其他类似框架的经验,你就能体会到根据不同条件拼接 SQL 语句有多么 ...

  7. mybatis的foreach标签

    今天写sql发现了一点问题,乱弄了好久算是搞定了.关于mybatis的批量插入使用foreach插入形式为: insert into role_privilege( role_id, privileg ...

  8. myBatis+Spring+SpringMVC框架面试题整理

    myBatis+Spring+SpringMVC框架面试题整理(一) 2018年09月06日 13:36:01 新新许愿树 阅读数 14034更多 分类专栏: SSM   版权声明:本文为博主原创文章 ...

  9. Mybatis中常用的SQL

    1.BaseResultMap <resultMap id="BaseResultMap" type="com.stylefeng.guns.common.pers ...

随机推荐

  1. nodejs03-GET数据处理

    数据请求:--- 前台:form ajax jsonp 后台:一样 请求方式: 1.GET 数据在URL中 2.POST 数据在请求体中 请求数据组成: 头--header:url,头信息 身子--c ...

  2. css实现标题左右横线

    最近用到了记录一下 页面 <div class="subtitle"> 马上邀请好友得奖励 </div> 样式 .subtitle { position: ...

  3. Oracle学习DayOne(SQL初步)

    一.DML.DDL.DCL SQL语句分为以下三种类型: DML: Data Manipulation Language 数据操纵语言DDL: Data Definition Language 数据定 ...

  4. flask 登录验证码 字母和数字

    captcha.py #!/usr/bin/env python# -*- coding: utf-8 -*- # refer to `https://bitbucket.org/akorn/whee ...

  5. electron-vue初始桌面应用

    1.安装vue-cli脚手架 npm install -g vue-cli 2.创建项目:vue init simulatedgreg/electron-vue my-project 3.安装依赖 : ...

  6. 五、stdout,stdoin和stderr

    stdout,stdin和stderr分别是标准输出流.标准输入流和标准错误流,当一个用户进程被创建的时候,系统会自动为该进程创建这三个数据流,默认情况下这三个流是在终端上表现出来的.可以使用fpri ...

  7. maven源码打包

    1.打包时附加外部Jar包 <!--编译+外部 Jar打包-->          <plugin>            <artifactId>maven-co ...

  8. vue中使用ajax

    var vue = new Vue({ el:"#vueid", data:{ selectById : "", }, methods:{ yourMethod ...

  9. 大数据处理N!(21<N<2000)

    输入: 每行输入1个正整数n,(0<n<1000 000) 输出: 对于每个n,输出n!的(十进制)位数 digit, 和最高位数firstNum.(n!约等于 firstNum * 10 ...

  10. python day31--网络编程,tcp,udp的指令,及黏包

    一.TCP tcp中遇到黏包会让数据传输完. server import socket sk=socket.socket() sk.bind(('127.0.0.1',8090)) sk.listen ...