日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

Mybatis中resultMap

發布時間:2025/3/11 编程问答 20 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Mybatis中resultMap 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

MyBatis中在查詢進行select映射的時候,返回類型可以用resultType,也可以用resultMap,resultType是直接
表示返回類型的,而resultMap則是對外部ResultMap的引用,但是resultType跟resultMap不能同時存在。

1.resultType

?

在MyBatis進行查詢映射的時候,其實查詢出來的每一個屬性都是放在一個對應的Map里面的,其中鍵是屬性名,
值則是其對應的值。當提供的返回類型屬性是resultType的時候,MyBatis會將Map里面的鍵值對取出賦給
resultType所指定的對象對應的屬性。所以其實MyBatis的每一個查詢映射的返回類型都是ResultMap,
只是當我們提供的返回類型屬性是resultType的時候,MyBatis對自動的給我們把對應的值賦給resultType
所指定對象的屬性,而當我們提供的返回類型是resultMap的時候,因為Map不能很好表示領域模型,
我們就需要自己再進一步的把它轉化為對應的對象,這常常在復雜查詢中很有作用。

?

這里要強調的是,Mybatis是對返回的結果的每一行做映射的。所以,下面的語句返回的是Integer,而不是List

?

?

Xml代碼??
  • <select?id="count"?parameterType="AreaDto"?resultType="java.lang.Integer">??
  • ????????SELECT?id?FROM?USER??
  • </select>??
  • ?

    返回一個int

    ?

    Xml代碼??
  • <select?id="count"?parameterType="AreaDto"?resultType="java.lang.Integer">??
  • ????????SELECT?count(*)?FROM?USER??
  • </select>??
  • ?

    返回map

    Xml代碼??
  • <select?id=”selectUsers”?parameterType=”int”?resultType=”hashmap”>??
  • ????select?id,?username,?hashedPassword??
  • ????from?some_table??
  • ????where?id?=?#{id}??
  • </select>??
  • ?

    這樣一個語句簡單作用于所有列被自動映射到HashMap的鍵上,這由resultType屬性指定。這在很多情況下是有用的,但是HashMap不能很好描述一個領域模型。那樣你的應用程序將會使用JavaBeans或POJOs(Plain Old Java Objects,普通Java對象)來作為領域模型

    返回javaBEAN 對象

    ?

    Xml代碼??
  • <select?id="count"?parameterType="AreaDto"?resultType="User">??
  • ????????SELECT?*?FROM?USER??
  • </select>???
  • ?

    要記住類型別名是你的伙伴。使用它們你可以不用輸入類的全路徑。

    ?

    Xml代碼??
  • <typeAlias?type=”com.someapp.model.User”?alias=”User”/>??
  • ?這些情況下,MyBatis會在幕后自動創建一個ResultMap,基于屬性名來映射列到JavaBean的屬性上

    ?

    2.resultMap

    ?

    MyBatis會自動創建一個ResultMap對象,然后基于查找出來的屬性名進行鍵值對封裝,然后再看到返回類型是Blog對象,再從ResultMap中取出與Blog對象對應的鍵值對進行賦值。

    當返回類型直接是一個ResultMap的時候也是非常有用的,這主要用在進行復雜聯合查詢上,因為進行簡單查詢是沒有什么必要的。

    ?

    簡單resultMap配置?

    ?

    Xml代碼??
  • <resultMap?type="com.liulanghan.Blog"?id="BlogResult">????
  • ????<id?column="id"?property="id"/>????
  • ????<result?column="title"?property="title"/>????
  • ????<result?column="content"?property="content"/>????
  • ????<result?column="owner"?property="owner"/>????
  • </resultMap>???
  • ???
  • <select?id="selectBlog"?parameterType="int"?resultMap="BlogResult">????
  • ??????select?*?from?t_blog?where?id?=?#{id}????
  • </select>??
  • ?

    結果集的列比resultMap多會報錯么?
    不會,只映射resultMap中有的列。

    ?

    結果集的列比resultMap少會報錯么?
    不會,只映射結果集中有的列。

    ?

    高級結果映射

    ?

    Xml代碼??
  • <resultMap?id="detailedBlogResultMap"?type="Blog">??
  • ????<constructor>??
  • ????????<idArg?column="blog_id"?javaType="int"/>??
  • ????</constructor>??
  • ????<result?property="title"?column="blog_title"/>??
  • ????<association?property="author"?column="blog_author_id"?javaType="?Author">??
  • ????????<id?property="id"?column="author_id"/>??
  • ????????<result?property="username"?column="author_username"/>??
  • ????????<result?property="password"?column="author_password"/>??
  • ????????<result?property="email"?column="author_email"/>??
  • ????????<result?property="bio"?column="author_bio"/>??
  • ????????<result?property="favouriteSection"?column="author_favourite_section"/>??
  • ????</association>??
  • ????<collection?property="posts"?ofType="Post">??
  • ????????<id?property="id"?column="post_id"/>??
  • ????????<result?property="subject"?column="post_subject"/>??
  • ????????<association?property="author"?column="post_author_id"?javaType="Author"/>??
  • ????????<collection?property="comments"?column="post_id"?ofType="?Comment">??
  • ????????????<id?property="id"?column="comment_id"/>??
  • ????????</collection>??
  • ????????<collection?property="tags"?column="post_id"?ofType="?Tag"?>??
  • ????????????<id?property="id"?column="tag_id"/>??
  • ????????</collection>??
  • ????????<discriminator?javaType="int"?column="draft">??
  • ????????????<case?value="1"?resultType="DraftPost"/>??
  • ????????</discriminator>??
  • ????</collection>??
  • </resultMap>??
  • ?

    ?

    resultMap
    ????? constructor – 類在實例化時,用來注入結果到構造方法中
    ?????????? idArg – ID參數;標記結果作為ID可以幫助提高整體效能
    ?????????? arg – 注入到構造方法的一個普通結果
    ????? id – 一個ID結果;標記結果作為ID可以幫助提高整體效能
    ????? result – 注入到字段或JavaBean屬性的普通結果
    ???? association – 一個復雜的類型關聯;許多結果將包成這種類型
    ????????? ?嵌入結果映射 – 結果映射自身的關聯,或者參考一個
    ???? collection – 復雜類型的集
    ?????????? 嵌入結果映射 – 結果映射自身的集,或者參考一個
    ??? discriminator – 使用結果值來決定使用哪個結果映射
    ???????? case – 基于某些值的結果映射
    ?????????????? 嵌入結果映射 – 這種情形結果也映射它本身,因此可以包含很多相同的元素,或者它可以參照一個外部的結果映射。

    ?

    ?

    id 和result
    ???
    id和result都映射一個單獨列的值到簡單數據類型

    ?

    這兩者之間的唯一不同是id表示的結果將是當比較對象實例時用到的標識屬性。這幫助來改進整體表現,特別是緩存和嵌入結果映射(也就是聯合映射)。

    ?

    它們共有的屬性如下:

    ?

    property

    ?

    映射到列結果的字段或屬性。如果匹配的是存在的,和給定名稱相同的JavaBeans的屬性,那么就會使用。否則MyBatis將會尋找給定名稱的字段。這兩種情形你可以使用通常點式的復雜屬性導航。比如,你可以這樣映射一些東西:“username”,或者映射到一些復雜的東西:“address.street.number”。

    ?

    column

    ?

    從數據庫中得到的列名,或者是列名的重命名標簽。這也是通常和會傳遞給resultSet.getString(columnName)方法參數中相同的字符串。

    ?

    javaType

    ?

    一個Java類的完全限定名,或一個類型別名(參加上面內建類型別名的列表)。如果你映射到一個JavaBean,MyBatis通常可以斷定類型。然而,如果你映射到的是HashMap,那么你應該明確地指定javaType來保證所需的行為。

    ?

    jdbcType

    ?

    在這個表格之后的所支持的JDBC類型列表中的類型。JDBC類型是僅僅需要對插入,更新和刪除操作可能為空的列進行處理。這是JDBC的需要,而不是MyBatis的。如果你直接使用JDBC編程,你需要指定這個類型-但僅僅對可能為空的值。

    ?

    typeHandler

    ?

    我們在前面討論過默認的類型處理器。使用這個屬性,你可以覆蓋默認的類型處理器。這個屬性值是類的完全限定名或者是一個類型處理器的實現,或者是類型別名。


    constructor

    ?

    。構造方法注入允許你在初始化時為類設置屬性的值,而不用暴露出公有方法。MyBatis也支持私有屬性和私有JavaBeans屬性來達到這個目的,但是一些人更青睞構造方法注入。

    為了向這個構造方法中注入結果,MyBatis需要通過它的參數的類型來標識構造方法。Java沒有自查(反射)參數名的方法。所以當創建一個構造方法元素時,保證參數是按順序排列的,而且數據類型也是確定的。

    ?

    association

    ?

    association關聯元素處理“有一個”類型的關系,即一對一關聯。它有兩種關聯方式

    ?

    嵌套查詢:通過執行另外一個SQL映射語句來返回預期的復雜類型。

    ?

    嵌套結果:使用嵌套結果映射來處理重復的聯合結果的子集。

    ?

    嵌套查詢

    ?

    Xml代碼??
  • <resultMap??id="userResultMap"?type="User">??
  • ????<id?property="id"?column="ID"?jdbcType="NUMERIC"?javaType="java.lang.Long"/>??
  • ????<result?property="loginName"?column="LOGIN_NAME"?jdbcType="VARCHAR"?javaType="java.lang.String"/>??
  • ????<result?property="password"?column="password"?jdbcType="VARCHAR"?javaType="java.lang.String"/>??
  • ????<result?property="roleId"?column="role_id"?jdbcType="NUMERIC"?javaType="java.lang.Long"/>??
  • ????<association?property="role"?column="role_id"?javaType="Role"?select="selectRole"/>??
  • </resultMap>??
  • ??
  • <select?id="selectUser"?parameterType="java.lang.Long"?resultMap="userResultMap"?>?????
  • ????select?*?from?User?where?id?=#{id}?????
  • </select>???
  • ??
  • <select?id="selectRole"?parameterType="java.lang.Long"?resultType="Role"?>?????
  • ????select?*?from?Role?where?id?=#{id}?????
  • </select>???
  • ?

    這里有兩個查詢,一個查詢加載User,一個查詢加載Role.
    這里select為另外一個映射語句的ID,可以加載這個屬性映射需要的復雜類型。獲取的在列屬性中指定的列的值將被傳遞給目標select語句作為參數。

    ?

    注意:
    而select 為selectRole的SQL輸入參數可以隨便給名稱,只要是輸入參數與壓入進去的值類型相同就行了,可以寫成:

    ?

    Xml代碼??
  • select?*?from?Role?where?id?=?#{sfffs}???
  • ?

    不管輸入參數名稱是什么,mybatis最終會執行:
    效果為:

    ?

    Sql代碼??
  • select?*?from?role?where?id?=resultSet.getLong("Role_id");??
  • ?

    注意:要保證第二個查詢查出來的結果只有一條記錄。

    ?

    要處理復合主鍵,你可以指定多個列名通過column="{prop1=col1,prop2=col2}"這種語法來傳遞給嵌套查詢語句。這會引起prop1和prop2以參數對象形式來設置給目標嵌套查詢語句。

    Xml代碼??
  • <resultMap??id="userResultMap"?type="User">??
  • ????<id?property="id"?column="ID"?jdbcType="NUMERIC"?javaType="java.lang.Long"/>??
  • ????<result?property="loginName"?column="LOGIN_NAME"?jdbcType="VARCHAR"?javaType="java.lang.String"/>??
  • ????<result?property="password"?column="password"?jdbcType="VARCHAR"?javaType="java.lang.String"/>??
  • ????<result?property="roleId"?column="role_id"?jdbcType="NUMERIC"?javaType="java.lang.Long"/>??
  • ????<association?property="role"?column="{id=role_id,name=role_name}"?javaType="Role"?select="selectRole"/>??
  • </resultMap>??
  • ??
  • <select?id="selectRole"?parameterType="HashMap"??resultType="Role"?>?????
  • ????select?*?from?Role?where?id?=#{id}?and?name=?#{name}?????
  • </select>??
  • ??

    這種方式很簡單,但是對于大型數據集合和列表將不會表現很好。問題就是我們熟知的“N+1查詢問題”。概括地講,N+1查詢問題可以是這樣引起的:


    ?? 你執行了一個單獨的SQL語句來獲取結果列表(就是“+1”)。
    ?? 對返回的每條記錄,你執行了一個查詢語句來為每個加載細節(就是“N”)。


    這個問題會導致成百上千的SQL語句被執行。這通常不是期望的。


    比如一個查詢用戶列表的SQL,假如有2000個用戶,那么就是一個查詢用戶的SQL和2000個查詢角色的SQL,一共有2001個SQL被運行。


    MyBatis能延遲加載這樣的查詢就是一個好處,因此你可以分散這些語句同時運行的消耗。然而,如果你加載一個列表,之后迅速迭代來訪問嵌套的數據,你會調用所有的延遲加載,這樣的行為可能是很糟糕的。

    ?

    所以還有另外一種方法。


    關聯的嵌套結果

    ?

    嵌套結果

    ?

    Xml代碼??
  • <resultMap??id="userResultMap"?type="User">??
  • ????<id?property="id"?column="ID"?jdbcType="NUMERIC"?javaType="java.lang.Long"/>??
  • ????<result?property="loginName"?column="LOGIN_NAME"?jdbcType="VARCHAR"?javaType="java.lang.String"/>??
  • ????<result?property="password"?column="password"?jdbcType="VARCHAR"?javaType="java.lang.String"/>??
  • ????<result?property="roleId"?column="role_id"?jdbcType="NUMERIC"?javaType="java.lang.Long"/>??
  • ????<association?property="role"?column="role_id"?javaType="Role"?resultMap="roleResultMap"/>??
  • ????????<id?property="id"?column="role_id"/>??
  • ????????<result?property="name"?column="role_name"/>??
  • ????</association>??
  • </resultMap>??
  • ??
  • <resultMap?id="roleResultMap"?type="Role">??
  • ????<id?property="id"?column="role_id"/>??
  • ????<result?property="name"?column="role_name"/>??
  • </resultMap>??
  • ?

    ?

    也可以這樣配置

    ?

    Xml代碼??
  • <resultMap??id="userResultMap"?type="User">??
  • ????<id?property="id"?column="ID"?jdbcType="NUMERIC"?javaType="java.lang.Long"/>??
  • ????<result?property="loginName"?column="LOGIN_NAME"?jdbcType="VARCHAR"?javaType="java.lang.String"/>??
  • ????<result?property="password"?column="password"?jdbcType="VARCHAR"?javaType="java.lang.String"/>??
  • ????<result?property="roleId"?column="role_id"?jdbcType="NUMERIC"?javaType="java.lang.Long"/>??
  • ????<association?property="role"?column="role_id"?javaType="Role"?resultMap="roleResultMap"/>??
  • </resultMap>??
  • ??
  • <resultMap?id="roleResultMap"?type="Role">??
  • ????<id?property="id"?column="role_id"/>??
  • ????<result?property="name"?column="role_name"/>??
  • </resultMap>??
  • ?

    ?resultMap這是結果映射的ID,可以映射關聯的嵌套結果到一個合適的對象圖中。這是一種替代方法來調用另外一個查詢語句。這允許你聯合多個表來合成到一個單獨的結果集。這樣的結果集可能包含重復,數據的重復組需要被分解,合理映射到一個嵌套的對象圖。為了使它變得容易,MyBatis讓你“鏈接”結果映射,來處理嵌套結果。一個例子會很容易來仿照,這個表格后面也有一個示例。

    ?

    注意這個聯合查詢,以及采取保護來確保所有結果被唯一而且清晰的名字來重命名。

    ?

    columnPrefix 屬性

    ?

    Xml代碼??
  • <association?property="role"?column="role_id"?javaType="Role"?resultMap="roleResultMap"?columnPrefix="role_"/>??
  • ????????<id?property="id"?column="id"/>??
  • ????????<result?property="name"?column="name"/>??
  • </association>??
  • ?

    非常重要:在嵌套據誒過映射中id元素扮演了非常重要的角色。應應該通常指定一個或多個屬性,它們可以用來唯一標識結果。實際上就是如果你離開她了,但是有一個嚴重的性能問題時MyBatis仍然可以工作。選擇的屬性越少越好,它們可以唯一地標識結果。主鍵就是一個顯而易見的選擇(盡管是聯合主鍵)。

    ?

    上面你已經看到了如何處理“有一個”類型關聯。但是“有很多個”是怎樣的?下面這個部分就是來討論這個主題的。

    ?

    collection

    ?

    collection關聯元素處理一對多關聯。

    ?

    Xml代碼??
  • <resultMap??id="roleResultMap"?type="Role">??
  • ????<id?property="id"?column="ID"?jdbcType="NUMERIC"?javaType="java.lang.Long"/>??
  • ????<result?property="name"?column="NAME"?jdbcType="VARCHAR"?javaType="java.lang.String"/>??
  • ????<result?property="userId"?column="user_id"?jdbcType="NUMERIC"?javaType="java.lang.Long"/>??
  • ????<collection?property="user"?column="user_id"?javaType="ArrayList"?ofType="Post"?select="selectUser"/>??
  • ??
  • </resultMap>??
  • ??
  • <select?id="selectUser"?parameterType="java.lang.Long"???resultType="User"?>?????
  • ????select?*?from?uer?where?id?=#{id}???
  • </select>???
  • ?

    同樣,可以這樣配置

    ?

    Xml代碼??
  • <resultMap??id="roleResultMap"?type="Role">??
  • ????<id?property="id"?column="ID"?jdbcType="NUMERIC"?javaType="java.lang.Long"/>??
  • ????<result?property="name"?column="NAME"?jdbcType="VARCHAR"?javaType="java.lang.String"/>??
  • ????<result?property="userId"?column="user_id"?jdbcType="NUMERIC"?javaType="java.lang.Long"/>??
  • ????<collection?property="user"?column="user_id"?javaType="ArrayList"?ofType="Post">??
  • ????????<id?property="id"?column="user_id"/>??
  • ????????<result?property="name"?column="user_name"/>??
  • ????</collection>??
  • </resultMap>??
  • <resultMap?id="userResultMap"?type="User">??
  • ????<id?property="id"?column="user_id"/>??
  • ????<result?property="name"?column="user_name"/>??
  • </resultMap>??
  • ??

    ?

    總結

    以上是生活随笔為你收集整理的Mybatis中resultMap的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。