(六) MyBatis從入門到入土——主鍵的獲取

這是mybatis系列第六篇。沒看前文的建議先去【Java冢狐】公衆號中查看前文,方便理解和掌握。java

前面五篇把MyBatis的基本用法基本介紹完畢了,強烈推薦你們先把前面五篇看完實際操做完再來看接下來的內容。mysql

增刪改返回值說明

mybatis中對db執行增刪改操做,不論是新增、刪除、仍是修改,其本質都是使用jdbc中對應的方法,即java.sql.Statement的executeUpdate的方法,或者java.sql.PreparedStatement的executeUpdate方法。sql

因此問題的關鍵在於掌握這兩個方法的內容,而這兩個方法的參數不一致可是返回值都是int,用來表示影響的行數。數據庫

而Mybatis的返回值再支持int的基礎上,還支持Integer、long、Long、boolean、Boolean、void多種類型,可謂是大大增強了編程的靈活性和多樣性。編程

可是聰明的小夥伴確定知道,MyBatis能支持這麼多種的類型,其實就是mybatis在內部將int類型轉換成其餘類型而已。沒有什麼高深的東西、api

瞭解了增刪改查的返回值後,下一步咱們再去看一看jdbc和mybatis是如何獲取主鍵的。mybatis

jdbc獲取主鍵的幾種方式

在聊jdbc獲取主鍵的方式以前,咱們先來回想一下數據庫的主鍵是怎麼樣生成的。多線程

那mysql舉例:在mysql中當咱們向表中插入數據的時候,若是不指定主鍵(id),那麼mysql會自動生成id,可是在一些業務中咱們後續會須要這個id,此時咱們就要想辦法去獲取這個id,尤爲是這種自動生成的自增id。併發

要想要清楚的瞭解,就須要先看看jdbc是如何實現的oracle

方式1:jdbc內置的方式

用法

獲取主鍵的需求,jdbc的開發人員就已經想到了,而且也開發了相應的api來幫助咱們編程,具體看 java.sql.Statement類中的getGeneratedKeys方法

從這個方法中咱們得知這個方法會返回一個結果集,從這個結果集中能夠獲取自增主鍵的值。可是在使用這個方法有個前提,那就是執行sql的時候須要作一個設置。

若是是經過java.sql.Statement執行sql,須要調用下面這個方法:

int executeUpdate(String sql, int autoGeneratedKeys) throws SQLException

注意上面這個方法的第二個參數須要設置爲java.sql.Statement.RETURN_GENERATED_KEYS,表示須要返回自增列的值。

不過多數狀況下,咱們會使用java.sql.PreparedStatement對象來執行sql,若是想獲取自增值,建立這個對象須要設置第2個參數的值,以下:

PreparedStatement preparedStatement = connection.prepareStatement(sql, Statement.RETURN_GENERATED_KEYS);

而後咱們就能夠經過getGeneratedKeys返回的ResultSet對象獲取自動增加的值了,以下:

ResultSet generatedKeys = preparedStatement.getGeneratedKeys();
if (generatedKeys!=null && generatedKeys.next()) {
    log.info("自增值爲:{}", generatedKeys.getInt(1));
}

方式2:插入以後查詢獲取

用法

固然除了jdbc想到了咱們這個需求,mysql數據庫也想到了這個需求也有對應的語句來幫助咱們在插入數據後獲取最新插入記錄的id值,以下所示

SELECT LAST_INSERT_ID()

因此咱們能夠在插入以後,當即使用當前鏈接發送上面這條sql去獲取自增列的值就能夠。這種方法相對來講十分的簡單和方便,可是也存在着一些問題,就是在高併發多線程的狀況 ,可能會出現嚴重的問題,因此通常來講不建議使用。

方式3:插入以前獲取

最後一種方法就是在插入以前獲取。

oracle不知道你們有沒有玩過,oracle中沒有mysql中自動增加列,可是oracle有個功能能夠實現自動增加,這個功能就是序列,序列就至關於一個自增器同樣,有個初始值,每次遞增的步長,固然這個序列提供了一些功能給咱們使用,能夠獲取序列的當前值、下一個值,使用方式以下:

  • 先定義一個序列
  • 獲取下一個值:SELECT 序列名.NEXTVAL FROM dual;

mybatis獲取主鍵的3種方式

既然jdbc有三種方法,那麼mybatis也有相應的幾種方法。

方式1:內部使用jdbc內置的方式

用法

mybatis這個方式內部採用的是上面說的jdbc內置的方式。

咱們須要在Mapper xml中進行配置,如:

<insert id="insertUser1" parameterType="zhonghu.mybatis.chat01.UserModel" useGeneratedKeys="true" keyProperty="id">
    <![CDATA[
    INSERT INTO user (name,age,salary) VALUES (#{name},#{age},#{salary})
     ]]>
</insert>

有2個關鍵參數必需要設置:

  • useGeneratedKeys:設置爲true
  • keyProperty:參數對象中的屬性名稱,最後插入成功以後,mybatis會經過反射將自增值設置給keyProperty指定的這個屬性

方式2:插入後查詢獲取主鍵

用法

這個方式和上面介紹的jdbc的第二種方式同樣,插入以後經過查詢獲取主鍵的值而後填充給指定的屬性,mapper xml配置以下:

<insert id="insertUser2" parameterType="zhonghu.mybatis.chat01.UserModel">
    <selectKey keyProperty="id" order="AFTER" resultType="long">
    <![CDATA[
    SELECT LAST_INSERT_ID()
     ]]>
    </selectKey>
    <![CDATA[
    INSERT INTO user (name,age,salary) VALUES (#{name},#{age},#{salary})
     ]]>
</insert>

關鍵代碼是selectKey元素包含的部分,這個元素內部能夠包含一個sql,這個sql能夠在插入以前或者插入以後運行(以前仍是以後經過order屬性配置),而後會將sql運行的結果設置給keyProperty指定的屬性,selectKey元素有3個屬性須要指定:

  • keyProperty:參數對象中的屬性名稱,最後插入成功以後,mybatis會經過反射將自增值設置給keyProperty指定的這個屬性
  • order:指定selectKey元素中的sql是在插入以前運行仍是插入以後運行,可選值(BEFORE|AFTER),這種方式中咱們選擇AFTER
  • resultType:keyProperty指定的屬性對應的類型,如上面的id對應的類型是java.lang.Long,咱們直接寫的是別名long

方式3:插入前查詢獲取主鍵

用法

這個方式和上面介紹的jdbc的第3種方式同樣,會在插入以前先經過一個查詢獲取主鍵的值而後填充給指定的屬性,而後在執行插入,mapper xml配置以下:

<insert id="insertUser3" parameterType="zhonghu.mybatis.chat01.UserModel">
    <selectKey keyProperty="id" order="BEFORE" resultType="long">
    <![CDATA[ 獲取主鍵的select語句 ]]>
    </selectKey>
    <![CDATA[
    INSERT INTO user (name,age,salary) VALUES (#{name},#{age},#{salary})
     ]]>
</insert>

關鍵代碼是selectKey元素包含的部分,這個元素內部能夠包含一個sql,這個sql能夠在插入以前或者插入以後運行(以前仍是以後經過order屬性配置),而後會將sql運行的結果設置給keyProperty指定的屬性,selectKey元素有3個屬性須要指定:

  • keyProperty:參數對象中的屬性名稱,最後插入成功以後,mybatis會經過反射將自增值設置給keyProperty指定的這個屬性
  • order:指定selectKey元素中的sql是在插入以前運行仍是插入以後運行,可選值(BEFORE|AFTER),這種方式中咱們選擇BEFORE
  • resultType:keyProperty指定的屬性對應的類型,如上面的id對應的類型是java.lang.Long,咱們直接寫的是別名long

總結

本篇文章着重介紹了mybatis中一些增刪改查的高級使用方法,尤爲是獲取主鍵的方法,在此進行了jdbc和mybatis對比介紹了三種方法。

最後

  • 若是以爲看完有收穫,但願能關注一下,順便給我點個贊,這將會是我更新的最大動力,感謝各位的支持
  • 歡迎各位關注個人公衆號【java冢狐】,專一於java和計算機基礎知識,保證讓你看完有所收穫,不信你打我
  • 求一鍵三連:點贊、轉發、在看。
  • 若是看完有不一樣的意見或者建議,歡迎多多評論一塊兒交流。感謝各位的支持以及厚愛。

——我是冢狐,和你同樣熱愛編程。

歡迎關注公衆號「Java冢狐」獲取最新消息

相關文章
相關標籤/搜索