MyBatis映射器中select等标签中sql的高级应用

写在前面

很久以前在有道云笔记上写的笔记,打算放弃它了,将笔记迁移到这里来。文章可能还有很多不足,请大家谅解,欢迎大佬提意见。

本文使用到的东西

  1. MyBatis
  2. java

1.正文

在映射其中,有select、update等标签,可以在这些标签中写sql查询语句

sql模糊查询实现

在映射器中不能直接连接字符串实现模糊查询,只能使用concat函数连接字符串
如下:

   <select id="findByOwner" parameterType="string" resultMap="HouseType">
      select house.*,pet.pname,pet.age,pet.feetcount from house,pet
      where house.owner like concat('%',#{owner},'%') and house.owner = pet.owner
   </select>

大于小于特殊符号表示:
在映射其中大于小于这些符号属于特殊符号不能直接输入,要转为对应的替代符号。
符号对应如下:

& &amp;
< &lt;
> &gt;
" &quot;
&apos;

如输入

select count(*) from manage where closure < 5

应表示为:

select count(*) from manage where closure  &lt; 5

动态SQL

在select、update等标签标签中存在等子标签,可以实现动态sql语句

< if>标签

语法:

<if test="判断语句">
判断正确sql查询就包含内容....
</if>
  • test属性表示判断语句的内容
  • 在if标签的test中判断int类型的数据会报错,
  • test中如果包含多条判断语句,语句之间用and、or连接

< where>标签

语法:

<where>
      自动给该内容添加“where”前缀,如果该内容以and、or开头,则自动删除and或or
</where>
  • 可以用于联合if做动态sql,删除因为第一条if内容没显示在头部多出来的and、or
  • where标签不会自动删除查询语句尾部的and或or

< set>标签

语法:

<set>
      自动给该内容添加“set”前缀,如果该内容以","结尾,则自动删除“,”
</set>
  • 可以用于联合if做动态sql,删除因为最后一条if内容没显示在尾部多出来的“,”
  • set标签不会自动删除查询语句头部的“,”

< trim>标签

语法:

<trim prefix="前缀" prefixOverrides="删除开头" suffixOverrides="删除结尾" suffix="后缀">
       自动给该内容添加prefix内的前缀,如果以prefixOverrides内容开头自动删除,如果以suffixOverrides内容结尾自动删除,自动添加suffix后缀
</trim>
  • trim标签灵活性很大,可以替代和标签的功能
  • prefix属性:自动给该标签内容添加一个前缀
  • prefixOverrides属性:如果trim标签内容以prefixOverrides指定的内容开头自动删除
  • suffix属性:自动给该标签内容添加一个后缀
  • suffixOverrides属性:如果trim标签内容以suffixOverrides指定的内容结尾自动删除

< where>+< if>动态sql示例

–如果uname或password为空,则查询语句中不包含给该内容,并自动删除头部多出来的and

   <select id="find" parameterType="Userinfo" resultMap="UserinfoType">
      select * from userinfo
      <where> 
         <if test="uname!=null">
            uname =#{uname}
         </if>
         <if test="password!=null">
            and password=#{password}
         </if>      
      </where>
      limit 0,1
   </select>

< set>+动态sql示例

–如果uname或password为空,则查询语句中不包含给该内容,并自动删除尾部多出来的“,”

   <update id="update" parameterType="Userinfo">
      update userinfo
      <set>
         <if test="uname!=null">
         uname=#{uname},
         </if>
         <if test="password!=null">
         password=#{password}
         </if>
      </set>
      where uid=#{uid}
   </update>

+取代+示例
–用实现标签的功能

    <select id="find" parameterType="Userinfo" resultMap="UserinfoType">
      select * from userinfo
      <trim prefix="where" prefixOverrides="and|or" suffix="limit 0,1">
         <if test="uname!=null">
            uname =#{uname}
         </if>      
         <if test="password!=null">
            and password=#{password}
         </if>
      </trim>        
   </select>

< trim>+取代+示例

–用实现标签的功能

   <update id="update" parameterType="Userinfo">
      update userinfo
      <trim prefix="set" suffixOverrides="," suffix="where uid=#{uid}">
         <if test="uname!=null">
         uname=#{uname},
         </if>
         <if test="password!=null">
         password=#{password}
         </if>
      </trim>     
   </update>

标签获取列表参数
假如传入的直接是java.util.List类的List对象
实例:
那么我们要将List类添加入MyBatis-config.xml中的的别名:

<typeAlias type="java.util.List" alias="List"/>

接口的传入参数定义为List或其他数据类型,例:

   public List<Userinfo> findUname(List<String> para);

在主类中调用:

      List<String> unames = new ArrayList<String>();//创建对象
      unames.add("lswe");//添加数据
      unames.add("lswe2");//添加数据
      //使用接口,传入一个List<String>对象
      List<Userinfo> list = dao.findUname(unames);

映射器中对应该接口的查询内容:

   <select id="findUname" parameterType="List" resultMap="UserinfoType">
      select * from userinfo
      <where>        
         <foreach collection="list" item="uname" open="uname in(" close=")" separator=",">
                      #{uname}
         </foreach>
      </where>      
   </select>
  • 上面实现的功能是 select * from userinfo where uname in(‘uname1’,‘uname2’,…)动态添加多个数据项
  • collection属性表示传入的列表或集合参数
  • item属性表示用于存储列表或集合中单个参数临时变量
  • open属性表示列表项的前缀
  • close属性表示列表项的后缀
  • separator表示用separator中的内容分隔列表项

假如传入的是java.util.List类的复杂对象类
实例:

自己定义一个封装类:
package com.etc.entity;
import java.util.List;
public class ArrayPara
{
   private List<String> unames;
   public List<String> getUnames() {
      return unames;
   }
   public void setUnames(List<String> unames) {
      this.unames = unames;
   } 
}

那么我们要将封装的对象类添加入MyBatis-config.xml中的的别名:

   <typeAlias type="com.etc.entity.ArrayPara" alias="ArrayPara"/>

接口的传入参数定义为List或其他数据类型,例:

   public List<Userinfo> findUname(ArrayPara ap);

映射器中对应该接口的查询内容:

   <select id="findUname" parameterType="ArrayPara" resultMap="UserinfoType">
      select * from userinfo
      <where>         
      <!-- unames是我们自定义的封装类的属性名 -->
         <foreach collection="unames" item="uname" open="uname in(" close=")" separator=",">
                      #{uname}
         </foreach>
      </where>      
   </select>

在主类中调用:

      List<String> unames = new ArrayList<String>();//创建对象
      unames.add("lswe");//添加数据
      unames.add("lswe2");//添加数据
      ArrayPara ap=new ArrayPara();
      ap.setUnames(unames);
      //使用接口,传入自己的封装类ArrayPara
      List<Userinfo> list = dao.findUname(ap);

< choose>映射器中的if…else…

格式:

<choose>
        <when test="判断语句">
            判断为true执行
        </when>
        <otherwise>
            判断为false执行
        </otherwise>
    </choose>

示例:

<choose>
        <when test="xxx !=null and xxx != ''">
            and xxx like concat(concat('%', #{xxx}), '%')
        </when>
        <otherwise>
            and xxx like '**%'
        </otherwise>
    </choose>
发布了38 篇原创文章 · 获赞 17 · 访问量 1230

猜你喜欢

转载自blog.csdn.net/nineya_com/article/details/103534268
今日推荐