mybatis其實就是ibatis 3.0,因此咱們以ibatis進行解釋,下面是mybatis執行原理:java
若是在service進行for循環,操做數據庫每次都要創建數據庫鏈接,執行SQL語句,而後釋放數據庫鏈接。若是把參數放到mybatis的xml進行執行,則能夠在第6步進行數據的批量更新、查詢等操做,只要一次鏈接就行。因此效率明顯提升了。node
補充名詞解釋:mysql
foreach的主要用在構建in條件中,它能夠在SQL語句中進行迭代一個集合。foreach元素的屬性主要有 item,index,collection,open,separator,close。item表示集合中每個元素進行迭代時的別名,index指 定一個名字,用於表示在迭代過程當中,每次迭代到的位置,open表示該語句以什麼開始,separator表示在每次進行迭代之間以什麼符號做爲分隔 符,close表示以什麼結束,在使用foreach的時候最關鍵的也是最容易出錯的就是collection屬性,該屬性是必須指定的,可是在不一樣狀況 下,該屬性的值是不同的,主要有一下3種狀況:sql
屬性 | 描述 |
---|---|
item | 循環體中的具體對象。支持屬性的點路徑訪問,如item.age,item.info.details。 具體說明:在list和數組中是其中的對象,在map中是value。 該參數爲必選。 |
collection | 要作foreach的對象,做爲入參時,List<?>對象默認用list代替做爲鍵,數組對象有array代替做爲鍵,Map對象沒有默認的鍵。 固然在做爲入參時可使用@Param("keyName")來設置鍵,設置keyName後,list,array將會失效。 除了入參這種狀況外,還有一種做爲參數對象的某個字段的時候。舉個例子: 若是User有屬性List ids。入參是User對象,那麼這個collection = "ids" 若是User有屬性Ids ids;其中Ids是個對象,Ids有個屬性List id;入參是User對象,那麼collection = "ids.id" 上面只是舉例,具體collection等於什麼,就看你想對那個元素作循環。 該參數爲必選。 |
separator | 元素之間的分隔符,例如在in()的時候,separator=","會自動在元素中間用「,「隔開,避免手動輸入逗號致使sql錯誤,如in(1,2,)這樣。該參數可選。 |
open | foreach代碼的開始符號,通常是(和close=")"合用。經常使用在in(),values()時。該參數可選。 |
close | foreach代碼的關閉符號,通常是)和open="("合用。經常使用在in(),values()時。該參數可選。 |
index | 在list和數組中,index是元素的序號,在map中,index是元素的key,該參數可選。 |
下面分別來看看上述三種狀況的示例代碼:數據庫
<select id="dynamicForeachTest" resultType="Blog"> select * from t_blog where id in <foreach collection="list" index="index" item="item" open="(" separator="," close=")"> #{item} </foreach> </select>
上述collection的值爲list,對應的Mapper是這樣的 :數組
public List<Blog> dynamicForeachTest(List<Integer> ids);
<select id="dynamicForeach2Test" resultType="Blog"> select * from t_blog where id in <foreach collection="array" index="index" item="item" open="(" separator="," close=")"> #{item} </foreach> </select>
上述collection爲array,對應的Mapper代碼: mybatis
public List<Blog> dynamicForeach2Test(int[] ids)
<select id="dynamicForeach3Test" resultType="Blog"> select * from t_blog where title like "%"#{title}"%" and id in <foreach collection="ids" index="index" item="item" open="(" separator="," close=")"> #{item} </foreach> </select>
上述collection的值爲ids,是傳入的參數Map的key,對應的Mapper代碼: app
public List<Blog> dynamicForeach3Test(Map<String, Object> params);
xml操做:spa
<update id="updateTestcaseNodeBatch" parameterType="List"> <foreach collection="list" item="nodeVO" separator=";"> UPDATE testcase_node <set> name=#{nodeVO.name}, version=#{nodeVO.version}, description=#{nodeVO.description}, last_modify_user=#{nodeVO.createUser}, last_modify_time=#{nodeVO.createTime} </set> <where> object_id=#{nodeVO.objectId} AND root_id=#{nodeVO.rootId} </where> </foreach> </update>
注意:若是報錯,多是下面的緣由:code
仔細檢查 map文件 和數據庫表字段沒有錯誤
最終結果是由於 配置的 mysql jdbc 連接字符串 默認不支持一次性執行多個sql 語句;
可是在咱們的 update map中須要執行多個 update語句。
最後加上參數 "allowMultiQueries" 設置爲true 以下:
<property name="jdbcUrl" value="jdbc:mysql://localhost:3306/test?useUnicode=true&characterEncoding=utf-8&allowMultiQueries=true" />