java版云笔记(九)之动态sql

SQL

  首先,所谓SQL的动态和静态,是凭SQL语句以何时给编译和履行,二者都是故当SQL嵌入式编程中之,这里所说的嵌入式是借助将SQL语句嵌入在高档语言中,而不是针对让仅片机的那种嵌入式编程。

静态SQL

  静态SQL通常用于完成得规定的天职。(即于编译阶段即可以规定数据库要开什么工作。)

select * from t1 where c1>5

  对于上述接近的DML语句以率先不行运行时展开编译,而连续再调用,则不再编译该过程。即一律蹩脚编译,多次调用,使用的相同的施行计划。此种方式受号称使用的凡静态的SQL。

注:

select * from t1 where c1>? and c2<?

  这种话语是静态SQL,不是动态SQL,虽然个别参数的价值未清楚,但普SQL的组织既规定,数据库是好将它们编译的,在实行等级就需要以分头参数的价加上即可。

动态SQL

  动态SQL通常是因此来因不同之急需就不同之任务。(在编译时无法确定,只有等到程序运行起来,在尽之进程中才能够确定,这种SQL叫做动态SQL。)

  如preparedStatement对象的execute方法去实施sql语句

作用:

  • 1 可以支持 DDL 语句, 静态 sql 只能支持 DML 语句.

  • 2 支持web 引用程序的询问意愿(
    一个网应用程序的大规模需求是用户可以指定他们想见到底排,
    以及变更多少的排序方式 )

  • 3 可以以事情逻辑先放在表中, 然后重新动态编译.

  今天我们讲的凡有关mybatis的动态sql

  通常使用动态 SQL 不容许是单独的平等有,MyBatis 当然使用同样种强大的动态
SQL 语言来改善这种场面,这种语言可以于用在肆意的 SQL 映射语句被。

  动态 SQL 元素和动用 JSTL 或任何类基于 XML 的文本处理器相似。在
MyBatis 之前的本子中,有众多之元素用来询问。MyBatis 3
大大升级了它们,现在因故非顶原一半之要素就可以了。MyBatis
采用功能强大的依据 OGNL 的表达式来扫除其他因素。

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

if

  动态 SQL 通常要举行的政工是生原则地含有 where 子句的相同片段。比如:

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

  这长长的告句提供了一个可选的文件查找类型的功用。如果无传来“title”,那么具有处于“ACTIVE”状态的BLOG都见面回到;反的而传入了“title”,那么就算会把模糊查找“title”内容之BLOG结果回到(就这事例而言,细心之读者会意识中的参数值是可蕴涵部分掩码或连配符的)。

  如果想然选地通过“title”和“author”两单极搜索该怎么收拾吧?首先,改变语句的称被它们再有着实际意义;然后如进入其他一个谱即可。

<select id="findActiveBlogLike"
     resultType="Blog">
  SELECT * FROM BLOG WHERE state = ‘ACTIVE’ 
  <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>

choose, when, otherwise

  有些上,我们无思就此到具备的法语句,而就想由中择其简单。针对这种情形,MyBatis
提供了 choose 元素,它多少像 Java 中之 switch 语句。

  还是地方的例子,但是这次变为提供了“title”就按照“title”查找,提供了“author”就照“author”查找,若两者都没有提供,就回来所有符合条件的BLOG(实际状况恐怕是由于管理员按自然策略选出BLOG列表,而休是归大量不论是意义的随意结果)。

    <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>

trim, where, set

  前面几只例证已经相应地缓解了一个臭名昭著的动态 SQL
问题。现在考虑回到“if”示例,这次咱们以“ACTIVE =
1”也安装成动态的条件,看看会发啊。

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>
    </select>

  如果这些条件从没一个能匹配上以见面怎样?最终就漫漫 SQL 会变成这样:

    SELECT * FROM BLOG
    WHERE

  立会招查询失败。如果就亚个条件相当又见面如何?这漫长 SQL
最终会是这么:

    SELECT * FROM BLOG
    WHERE 
    AND title like ‘someTitle’

  其一查询也会见砸。这个问题非能够大概的故口径句式来化解,如果你为曾经被迫这样描绘了,那么您非常可能以后以后还不思量再这么去写了。

  MyBatis
有一个简便的拍卖,这当90%底情景下都见面出因此。而当无能够使的地方,你得自定义处理方式来使其常规干活。一处简易的修改就能得到想使的机能:

<where>包裹 </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>
      </where>
    </select>

  where
元素知道只有以一个以上之if条件有值的状下才去插入“WHERE”子句。而且,若最终之情节是“AND”或“OR”开头的,where
元素也清楚什么样将她们去。

trim

  如果 where 元素没有按照正常套路出牌,我们还是得由此打定义 trim
元素来定制我们想如果的效益。比如,和 where 元素等价格的自定义 trim 元素为:

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

  prefixOverrides
属性会忽略通过管道相隔的公文序列
(注意此例中的空格也是必备之)。它带的结果就是是负有
prefixOverrides 属性中指定的内容以吃移除
,并且插入 prefix
属性中指定的情节。

set

  类似之用来动态更新语句的缓解方案叫做 set。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 元素会动态前置 SET
关键字,同时为会见败无关的逗号,因为用了尺度语句之后好可能就是会在变化的赋值语句之后边留下这些逗号

  若您对顶价格的自定义 trim 元素的金科玉律感兴趣,那立就是相应是她的精神:

    <trim prefix="SET" suffixOverrides=",">
      ...
    </trim>

  注意这里我们忽略的凡继缀着的价,而还要平等涂鸦附加了前缀着的价值。

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
元素的法力是蛮强劲的,它许你指定一个聚众,声明可以就此当要素体内的集合项和目录变量。其为允许你指定开闭匹配的字符串以及当迭代中间放置分隔符。这个因素是十分智能的,因此她不会见有时地附加多余的分隔符。

  注意
你可以以另可迭代对象(如列表、集合等)和其余的字典或者数组对象传递让foreach作为集参数。

  •   当用可迭代对象或数组时,index是当前迭代的次数,item的价值是此次迭代获取之素

  •   当以字典(或者Map.Entry对象的汇聚)时,index是键,item是值

  到者我们曾完成了涉及 XML 配置文件与 XML
映射文件之讨论。下一部分用详细探索 Java
API,这样才能够由曾开立的映照中得到最可怜便宜。

bind(创建变量并包扎)

  bind 元素可以于 OGNL
表达式中创一个变量并拿该绑定到上下文。比如:

    <select id="selectBlogsLike" resultType="Blog">
      <bind name="pattern" value="'%' + _parameter.getTitle() + '%'" />
      SELECT * FROM BLOG
      WHERE title LIKE #{pattern}
    </select>

Multi-db vendor support(多数据库厂商支持)

  一个配置了**“_databaseId”变量的 databaseIdProvider
对于动态代码来说是可用之,这样就是得
根据不同的数据库厂商构建特定的话语**。比如下面的例证:

    <insert id="insert">
      <selectKey keyProperty="id" resultType="int" order="BEFORE">
        <if test="_databaseId == 'oracle'">
          select seq_users.nextval from dual
        </if>
        <if test="_databaseId == 'db2'">
          select nextval for seq_users from sysibm.sysdummy1"
        </if>
      </selectKey>
      insert into users values (#{id}, #{name})
    </insert>

  至此,关于出口笔记涉及的学识就谈得了了,大家可以仔细看,看甚知识带动您没有来看好好好看看

网站地图xml地图