zoukankan      html  css  js  c++  java
  • MyBatis动态SQL

      根据不同的条件,需要执行不同的SQL 命令.称为动态SQL。例如如下需求,我们需要根据姓名和手机号去查询person的数据,那么:

    1. 当姓名和手机号参数不传值时,执行的sql应该是:
    select * from person
    
    1. 当只传姓名时,执行的sql应该是:
    select * from person where name = 'xxx'
    
    1. 当只传手机号时,执行的sql应该是:
    select * from person where phone = 'xxx'
    
    1. 当姓名和手机号都传递时,执行的sql应该是:
    select * from person where name = 'xxx' and phone = 'xxx'
    

      如果上面这种处理逻辑要在service或dao中进行处理时,会比较麻烦,这个时候,就可以使用上动态SQL了,利用MyBatis 中的动态SQL 在mappxml中添加逻辑判断等。

    1. <if>

    <select id="selByAccinAccout" resultType="log">
      select * from log where 1=1
    <!-- OGNL 表达式,直接写 key 或对象的属性.不需要添加任何特字符号 -->
      <if test="accin!=null and accin!=''">
        and accin=#{accin}
      </if>
      <if test="accout!=null and accout!=''">
        and accout=#{accout}
      </if>
    </select>
    

    2.<where>

    • 当编写 where 标签时,如果内容中第一个是 and, 则会去掉第一个and关键字
    • 如果<where>中有内容,则会生成 where 关键字,如果没有内容则不生成where 关键字
    <select id="selByAccinAccout" resultType="log">
       select * from log
       <where>
         <if test="accin!=null and accin!=''">
           and accin=#{accin}
         </if>
         <if test="accout!=null and accout!=''">
           and accout=#{accout}
         </if>
       </where>
    </select>
    

      可以看到,实现同样的功能,使用<where>比直接使用<if>少写了where 1=1

    3.<choose> <when> <otherwise>

      只要有一个成立,其他的就都不执行

    <select id="selByAccinAccout" resultType="log">
       select * from log
    	<where>
    		<choose>
    			<when test="accin!=null and accin!=''">
    				and accin=#{accin}
    			</when>
    			<when test="accout!=null and accout!=''">
    				and accout=#{accout}
    			</when>
    		</choose>
    	</where>
    </select>
    

      根据上面的sql,当accin 和accout 都不是null 且都不是""时,即当两个<when>都判断成立时,生成的sql 中只有where accin=?,即第一个。

    4.<set>

      <set>用在更新(upadte)数据库的时候使用。先来直接看mapper.xml的书写:

    <update id="upd" parameterType="log" >
    	update log
    	<set>
    		id=#{id},
    		<if test="accIn!=null and accIn!=''">
    			accin=#{accIn},
    		</if>
    		<if test="accOut!=null and accOut!=''">
    			accout=#{accOut},
    		</if>
    		</set>
    	Where id=#{id}
    </update>
    

      <set>用来修改SQL 中set 从句。

    1. 如果<set>里面有内容生成set 关键字,没有就不生成。
    2. <set>会自动去掉生成的sql中的最后一个逗号。
    3. 注意到上面的sql中有个id=#{id},它的目的是 防止中没有内容,mybatis 不生成 set 关键字,如果update中没有set 从句,则SQL语法错误.

    5.<Trim>

    1. prefix 在前面添加内容
    2. prefixOverrides 去掉前面内容
    3. suffix 在后面添加内容
    4. suffixOverrieds 去掉后面内容
    5. 执行顺序:去掉内容后添加内容
    <update id="upd" parameterType="log"> update log
      <trim prefix="set" suffixOverrides=",">
         a=a,
      </trim>
     where id=100
    </update>
    

    5.<bind>

      作用:给参数重新赋值
      使用场景:
        1)模糊查询
        2)在原内容前或后添加内容

      示例:

    <select id="selByLog" parameterType="log" resultType="log">
      <bind name="accin" value="'%'+accin+'%'"/>
       #{money}
    </select>
    

    6.<foreach>

    循环参数内容,还具备在内容的前后添加内容,还具备添加分隔符功能.

    适用场景

    1. in查询

    主要应用的其实就是in查询。
    2. 批量新增中(mybatis 中 foreach 效率比较低)
      2.1如果希望批量新增,SQL 命令:

    insert into log VALUES(default,1,2,3),(default,2,3,4),(default,3,4,5)
    

    2.2 openSession()必须指定
      底层是JDBC 的PreparedStatement.addBatch();

    factory.openSession(ExecutorType.BATCH);
    

    示例

    • collectino=”” 要遍历的集合
    • item 迭代变量名,然后通过 #{迭代变量名}获取内容
    • open 循环后左侧添加的内容
    • close 循环后右侧添加的内容
    • separator 每次循环时,元素之间的分隔符
    <select id="selIn" parameterType="list" resultType="log">
    	select * from log where id in
    	<foreach collection="list" item="abc" open="(" close=")" separator=",">
    		#{abc}
    	</foreach>
    </select>
    

    7.<sql> 和<include>

    1. 某些SQL 片段如果希望复用,可以使用<sql>定义这个片段
    <sql id="mysql">
       id,accin,accout,money
    </sql>
    
    1. 在<select>或<delete>或<update>或<insert>中使用<include> 引用
    <select id="">
    	select <include refid="mysql"></include>
    	from log
    </select>
    
  • 相关阅读:
    Encrypted Handshake Message
    RSAParameters Struct
    What if JWT is stolen?
    What's the difference between JWTs and Bearer Token?
    RSA Algorithm Example
    第18届Jolt大奖结果公布
    Ruby on rails开发从头来(windows)(三十六) 调试技巧
    Ruby on rails开发从头来(四十二) ActiveRecord基础(主键和ID)
    YouTube开放基础技术架构 让用户建自家YouTube
    Ruby on rails开发从头来(四十) ActiveRecord基础(Boolean属性)
  • 原文地址:https://www.cnblogs.com/suhaha/p/11798299.html
Copyright © 2011-2022 走看看