1. 程式人生 > >mybatis學習之路----動態sql之if條件判斷各種使用方式

mybatis學習之路----動態sql之if條件判斷各種使用方式

點滴記載,點滴進步,願自己更上一層樓。

由於需要看到效果,所以這節最好可以將sql語句打印出來。參考 mybatis學習之路----列印sql語句

mybatis的if判斷語句其實跟el表示式的if條件判斷有些類似。

例如: <if test="id != null"> </if>

1 如果引數為數字型別的時候沒有特俗需求的情況只需要判斷是否為null即可。

例如:<if test="id != null"></if>

 如果有特俗需求,例如判斷是否大於某個數的時候才行。只需要加上對應的條件判斷即可

例如:<if test='id != null and id > 28'></if>

 mybatis對於這種大於小於等等還有另一種形式。

例如:<if test='id != null and id gt 28'></if>

對應關係:

---------------------------------------

    gt            對應             >

    gte         對應              >=

    lt             對應              <(會報錯  相關聯的 "test" 屬性值不能包含 '<' 字元)

    lte          對應               <=(會報錯  相關聯的 "test" 屬性值不能包含 '<' 字元)

---------------------------------------

2 如果為字串型別

2.1 如果不需要過濾空串的情況 僅僅判斷null即可

例如:<if test="username != null"></if>

2.2 如果需要過濾空串,新增空串判斷即可  不支援 &&   所以這裡用 and  or  || 來做邏輯與或的判斷 

例如:<if test="username != null and '' != username"></if> 或者 <if test="username != null and ''  neq username"></if>

2.3 如果判斷字串是否已某個特俗字元開頭,結尾等。直接呼叫String的對應方法即可

例如:<if test="username != null and username.indexOf('ji') == 0"> </if> <!-- 是否以什麼開頭 -->     <if test="username != null and username.indexOf('ji') >= 0"> </if> <!-- 是否包含某字元 -->     <if test="username != null and username.lastIndexOf('ji') > 0"></if>  <!-- 是否以什麼結尾 -->

2.4 是否是某個特定字串,某些業務有此需要。

例如:<if test="username != null and 'hello' == username"></if> 或者<if test="username != null and 'hello' eq username"></if>

注意:

<if test="username != null and 'hello' == username"></if>這種形式的寫法在引數型別是字串的時候是沒有問題的,

但是引數型別為非字串型別的時候就需要寫成 <if test="username != null and 'hello'.toString() == username.toString()"></if>

僅僅寫成<if test="username != null and 'hello'.toString() == username"></if>也會有很大可能會掛。

也許你會說非字串的為什麼要寫成這樣。這就要看特俗需要了。

例如:某一個sql片段是公用的,

<if test="username != null"></if> <if test="password != null"></if>

該片段更新條件也用,但是當你需要將某一個欄位更新成null的時候怎麼辦。

這個時候就可以通過傳入一個特定的字串來弄。當傳入的字串為特定字串的時候就更新該字串為null。

<if test="username != null and 'hello'.toString() == username.toString()">xxx=null</if>

當然這樣子貌似date型會掛。

通過 2.2 也可以看出mybatis對於字串的相等不相等的判斷也是有對應的特俗操作符的。

-------------------------------------------------------

eq                  對應                ==

neq               對應                 !=

------------------------------------------------------

當然還可以看出來if的條件判斷test是支援物件自身方法呼叫的,即使是自己寫的方法,可以自己嘗試。當然下面會有例子。

例如:裡面可以用‘xxxx’.equals(xxxx) 字串的比較兩個字串方法

    xxxx.indexOf('ss') 判斷字串裡面是否包含某個字元等等  

 3 判斷list是否為空

上面說過,if條件判斷可以直接呼叫物件自身的方法進行邏輯判斷,所以list判空。可以呼叫.size()>0或者.isEmpty()

例如:<if test="userList != null and userList.isEmpty()"></if> , <if test="userList != null and userList.size()>0"></if>

4 map引數同同理  取值的話 map.key(map中的key名字)即可

----------------------------------------------------------------------------------------------分割線01-----------------------------------------------------------------------------------------------------------

這裡是上面的各種理論的實踐。這裡可以不看,自己去實踐最好。

1 數字型別。

僅作null判斷。

 <!--if 標籤使用類似html的C標籤的if -->     <select id="selectUseIf" parameterType="com.soft.test.model.DynamicTestModel" resultMap="userMap">         select * from t_user where 1=1         <if test='id != null'>             and id=#{id}         </if>     </select> 當id不為null的時候 列印的log DEBUG [main] - ==>  Preparing: select * from t_user where 1=1 and id=?  DEBUG [main] - ==> Parameters: 28(Integer) DEBUG [main] - <==      Total: 1

當id為null的時候 列印的log DEBUG [main] - ==>  Preparing: select * from t_user where 1=1  DEBUG [main] - ==> Parameters:  DEBUG [main] - <==      Total: 1

兩項對比,可以看出id=?這個條件隨著傳入引數id的變化而變化。

當有特俗需求的時候,當前資料庫中的表id為28 僅僅有這麼一條資料,做一下輕微的改動

<if test='id != null and id > 27 '> 當傳入id=28的時候 DEBUG [main] - ==>  Preparing: select * from t_user where 1=1 and id=?  DEBUG [main] - ==> Parameters: 28(Integer) DEBUG [main] - <==      Total: 1

當傳入id小於28的時候

DEBUG [main] - ==>  Preparing: select * from t_user where 1=1  DEBUG [main] - ==> Parameters:  DEBUG [main] - <==      Total: 1

接下來測試下面這幾種對應關係。

---------------------------------------

    gt            對應             >

    gte         對應              >=

    lt             對應              <(會報錯  相關聯的 "test" 屬性值不能包含 '<' 字元)

            lte          對應               <=(會報錯  相關聯的 "test" 屬性值不能包含 '<' 字元)

---------------------------------------

gt    <if test='id != null and id gt 27 '> 引數  id=25 DEBUG [main] - ==>  Preparing: select * from t_user where 1=1  DEBUG [main] - ==> Parameters:

引數  id=28 DEBUG [main] - ==>  Preparing: select * from t_user where 1=1 and id=?  DEBUG [main] - ==> Parameters: 28(Integer)

 >= 

<if test='id != null and id >= 28 '> 引數  id=28 DEBUG [main] - ==>  Preparing: select * from t_user where 1=1 and id=?  DEBUG [main] - ==> Parameters: 28(Integer)

引數  id=27

DEBUG [main] - ==>  Preparing: select * from t_user where 1=1  DEBUG [main] - ==> Parameters: 

gte   

<if test='id != null and id gte 28 '> 引數  id=28 DEBUG [main] - ==>  Preparing: select * from t_user where 1=1 and id=?  DEBUG [main] - ==> Parameters: 28(Integer)

引數  id=27

DEBUG [main] - ==>  Preparing: select * from t_user where 1=1  DEBUG [main] - ==> Parameters: 

    使用 <   <= 直接報錯       "test" 屬性值不能包含 '<' 字元 看來只能用 lt   lte了

lt

<if test='id != null and id lt 28 '> 引數  id=28   DEBUG [main] - ==>  Preparing: select * from t_user where 1=1  DEBUG [main] - ==> Parameters:  引數  id=27

DEBUG [main] - ==>  Preparing: select * from t_user where 1=1 and id=?  DEBUG [main] - ==> Parameters: 27(Integer)

lte

<if test='id != null and id lte 28 '> 引數  id=28  

DEBUG [main] - ==>  Preparing: select * from t_user where 1=1 and id=?  DEBUG [main] - ==> Parameters: 28(Integer)

引數  id=29

DEBUG [main] - ==>  Preparing: select * from t_user where 1=1  DEBUG [main] - ==> Parameters: 

----------------------------------------------------------------------------------------------分割線02-----------------------------------------------------------------------------------------------------------

2.1 跟1的第一條一樣不做重複測試

2.2 過濾空串

 <select id="selectUseIf" parameterType="com.soft.test.model.DynamicTestModel" resultMap="userMap">         select * from t_user where 1=1         <if test="username != null and '' != username ">             and username=#{username}         </if>     </select> != username=“xiao” DEBUG [main] - ==>  Preparing: select * from t_user where 1=1 and username=?  DEBUG [main] - ==> Parameters: xiao(String)

username=“”

DEBUG [main] - ==>  Preparing: select * from t_user where 1=1  DEBUG [main] - ==> Parameters: 

neq

<if test="username != null and '' neq username "> username=“xiao”

DEBUG [main] - ==>  Preparing: select * from t_user where 1=1 and username=?  DEBUG [main] - ==> Parameters: xiao(String)

username=“”

DEBUG [main] - ==>  Preparing: select * from t_user where 1=1  DEBUG [main] - ==> Parameters: 

各個邏輯與或的判斷 and上面已經弄過了,這裡弄or  || 兩種條件  

<if test="'xiaohong' eq username or 'xiao' eq username "> or

username=“xiao”

DEBUG [main] - ==>  Preparing: select * from t_user where 1=1 and username=?  DEBUG [main] - ==> Parameters: xiao(String) username=“xiaohong” DEBUG [main] - ==>  Preparing: select * from t_user where 1=1 and username=?  DEBUG [main] - ==> Parameters: xiaohong(String)

username=“xiaofang”

DEBUG [main] - ==>  Preparing: select * from t_user where 1=1  DEBUG [main] - ==> Parameters: 

||

username=“xiao”

DEBUG [main] - ==>  Preparing: select * from t_user where 1=1 and username=?  DEBUG [main] - ==> Parameters: xiao(String)

username=“xiaohong”

DEBUG [main] - ==>  Preparing: select * from t_user where 1=1 and username=?  DEBUG [main] - ==> Parameters: xiaohong(String)

username=“xiaofang”

DEBUG [main] - ==>  Preparing: select * from t_user where 1=1  DEBUG [main] - ==> Parameters: 

2.3  indexOf()  lastIndexOf()  判斷是否包含某個特定字元 <if test="username != null and username.indexOf('xiao')==0"> username=“xiao”

DEBUG [main] - ==>  Preparing: select * from t_user where 1=1 and username=?  DEBUG [main] - ==> Parameters: xiao(String)

username=“xiaofang”

DEBUG [main] - ==>  Preparing: select * from t_user where 1=1 and username=?  DEBUG [main] - ==> Parameters: xiaofang(String) 其他兩個沒什麼大不同的。自行測試。 2.4   判斷是否是某個字元

<if test="'xiaohong' eq username"> username=“xiaohong” ==>  Preparing: select * from t_user where 1=1 and username=?  ==> Parameters: xiaohong(String)

username=“xiaofang”

==>  Preparing: select * from t_user where 1=1  ==> Parameters: 

3  4  的本質就是再說mybatis的if條件判斷語句可以直接執行物件的方法。下面自己寫一個方法,在if裡面試試。

自己定義一個類,裡面一個方法用於條件判斷用。

public class DynamicSql1Model {     public boolean getMySelfMethod(){         return true;     } } 該類作為一個屬性放入到model中  僅僅貼出部分程式碼 public class DynamicSqlModel {     private int id;     private String username;     private String password;     private Date createDate;     private List<String> list;     private Map<String,Object> mapParam;       private DynamicSql1Model dynamicSql1Model; xml中引用該model的方法  <if test="dynamicSql1Model.getMySelfMethod()"> 開始測試 DynamicSqlModel user = new DynamicSqlModel();         user.setUsername("xiaofang");         user.setPassword("123456");         user.setCreateDate(new Date());         DynamicSql1Model dynamicSqlModel = new DynamicSql1Model();         user.setDynamicSql1Model(dynamicSqlModel);         dao.selectUseIf(user); 現在返回結果 現在方法的返回值為true  ==>  Preparing: select * from t_user where 1=1 and username=?  ==> Parameters: xiaofang(String) 方法返回值修改為false

==>  Preparing: select * from t_user where 1=1  ==> Parameters:  可以看出完全可以使用自定義的方法進行if條件控制。通過該特性可以幹一些特俗業務的事情。自己體會。

本篇說的主要是if條件判斷動態控制sql。可以看出有弊端。因為if條件不滿足的時候sql會變成

select * from t_user where  所以我在條件後面加了個 1=1 但是這是不符合邏輯的。下節介紹where以及其他標籤用於動態sql。

---------------------  作者:第一小菜鳥  來源:CSDN  原文:https://blog.csdn.net/xu1916659422/article/details/78104976  版權宣告:本文為博主原創文章,轉載請附上博文連結!