欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

MyBatis嵌套查詢collection報錯:org.apache.ibatis.exceptions.TooManyResultsException

 更新時間:2024年09月27日 11:07:05   作者:永不服輸?shù)腸oder  
本文主要介紹了MyBatis嵌套查詢collection報錯:org.apache.ibatis.exceptions.TooManyResultsException,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧

1、目標(biāo)

本文的主要目標(biāo)是研究resultMap的collection更新字段但是resultMap不更新字段報錯的原因和源碼分析

2、resultMap的collection更新字段,resultMap不更新字段會報錯

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="org.apache.mybatisDemo.ClassMapper">
    <resultMap id="classMap" type="org.apache.mybatisDemo.Class">
        <!--<id property="id" column="classId"/>-->
        <!--<result property="name" column="className"/>-->
        <!--<result property="createTime" column="create_time"/>-->
        <collection property="stuList" javaType="java.util.List" ofType="org.apache.mybatisDemo.Stu">
            <result property="id" column="stuId"/>
            <result property="name" column="stuName"/>
            <result property="age" column="age"/>
        </collection>
    </resultMap>

    <select id="getClass" resultMap="classMap">
        select c.id classId, c.name className, c.create_time, s.id stuId, s.name stuName, s.age
        from `class` c inner join `stu` s on c.id = s.class_id
        where c.`name` = #{className}
    </select>
</mapper>

如果不更新resultMap是classMap的字段只更新resultMap的collection字段會報錯

在這里插入圖片描述

報錯信息是不能返回多個記錄,因為調(diào)用了selectOne方法只返回1個記錄,那為什么會返回多個記錄呢,因為封裝成多個Class班級對象了

源碼分析:

在這里插入圖片描述

查詢數(shù)據(jù)庫得到多個記錄后會調(diào)用handleRowValuesForNestedResultMap方法處理嵌套屬性

在這里插入圖片描述

會循環(huán)遍歷查詢數(shù)據(jù)庫的每個記錄,并封裝成Class班級對象

在這里插入圖片描述

計算combinedKey的時候會判斷collection的更新字段至少為1并且父節(jié)點(diǎn)resultMap的更新字段至少為1才會更新combinedKey,否則更新combinedKey是NULL_CACHE_KEY

這里由于resultMap(classMap)的更新字段為0,因此combinedKey是NULL_CACHE_KEY

在這里插入圖片描述

調(diào)用getRowValue方法查詢數(shù)據(jù)庫的記錄

在這里插入圖片描述

會調(diào)用ObjectFactory對象的create方法實例化一個Class班級對象

在這里插入圖片描述

這里判斷combinedKey等于NULL_CACHE_KEY,因此不會將這個Class班級對象放到nestedResultObjects這個map中

在這里插入圖片描述

while循環(huán)查詢數(shù)據(jù)庫的第二條記錄的時候,從nestedResultObjects這個map中沒有找到Class班級對象就會創(chuàng)建一個新的Class班級對象,這樣會返回多個Class班級對象

在這里插入圖片描述

list集合中添加嵌套王五2Stu對象的Class班級對象,這樣的話會返回3個Class班級對象

在這里插入圖片描述

最終查詢數(shù)據(jù)庫返回3個Class班級對象

在這里插入圖片描述

調(diào)用selectOne方法查詢數(shù)據(jù)庫記錄是3個會拋出異常:期望1個返回值結(jié)果返回多個

3、resultMap的collection和resultMap都更新字段不會報錯

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="org.apache.mybatisDemo.ClassMapper">
    <resultMap id="classMap" type="org.apache.mybatisDemo.Class">
        <id property="id" column="classId"/>
        <result property="name" column="className"/>
        <result property="createTime" column="create_time"/>
        <collection property="stuList" javaType="java.util.List" ofType="org.apache.mybatisDemo.Stu">
            <result property="id" column="stuId"/>
            <result property="name" column="stuName"/>
            <result property="age" column="age"/>
        </collection>
    </resultMap>

    <select id="getClass" resultMap="classMap">
        select c.id classId, c.name className, c.create_time, s.id stuId, s.name stuName, s.age
        from `class` c inner join `stu` s on c.id = s.class_id
        where c.`name` = #{className}
    </select>
</mapper>

resultMap更新字段大于1,并且resultMap的collection的更新字段也大于1

在這里插入圖片描述

最后輸出結(jié)果正確,是一個Class班級對象,同時封裝了三個Stu對象

源碼分析:

public CacheKey clone() throws CloneNotSupportedException {
    CacheKey clonedCacheKey = (CacheKey) super.clone();
    clonedCacheKey.updateList = new ArrayList<>(updateList);
    return clonedCacheKey;
  }

執(zhí)行CacheKey的clone方法可以深拷貝CacheKey對象,這里CacheKey重寫了clone方法,因為CacheKey有一個list集合的屬性updateList,需要手動深拷貝復(fù)制list集合屬性

在這里插入圖片描述

生成combinedKey的時候會判斷resultMap的collection的更新字段至少有一個,并且resultMap的更新字段至少有一個,才會更新combinedKey,否則combinedKey設(shè)置成默認(rèn)key即NULL_CACHE_KEY

這里combinedKey=-1902729450:-2918070140:org.apache.mybatisDemo.ClassMapper.mapper_resultMap[classMap]_collection[stuList]:stuId:4:stuName:張三2:age:15:680594160:-729303444:org.apache.mybatisDemo.ClassMapper.classMap:classId:2

它由兩部分組成,第一部分是collection的key和value,第二部分是classMap這個Class班級對象

在這里插入圖片描述

如果combinedKey不為默認(rèn)key即NULL_CACHE_KEY,才會將查詢數(shù)據(jù)庫的記錄緩存到nestedResultObjects這個map中

在這里插入圖片描述

查詢數(shù)據(jù)庫的第二條記錄的時候才會從nestedResultObjects這個map中獲取緩存的Class班級對象,同時這個Class班級對象還嵌套了第一條記錄即張三2Stu對象

在這里插入圖片描述

查詢的數(shù)據(jù)庫記錄是一個記錄,它是Class班級對象,它包含了stuList屬性,它是一個list集合類型,它包括3個Stu對象

4、總結(jié)

在這里插入圖片描述

總結(jié)一句話:resultMap的collection更新字段至少為1個,并且resultMap的更新字段至少為1個,才會返回一個嵌套了多個Stu對象的Class班級對象,否則會返回多個Class班級對象

到此這篇關(guān)于MyBatis嵌套查詢collection報錯:org.apache.ibatis.exceptions.TooManyResultsException的文章就介紹到這了,更多相關(guān)MyBatis嵌套查詢collection報錯內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • 詳解FutureTask如何實現(xiàn)最大等待時間

    詳解FutureTask如何實現(xiàn)最大等待時間

    這篇文章主要為大家詳細(xì)介紹了如何從源碼中了解FutureTask實現(xiàn)最大等待時間的方法,文中的示例代碼講解詳細(xì),感興趣的可以了解一下
    2023-03-03
  • IDEA之翻譯器的使用Translation

    IDEA之翻譯器的使用Translation

    這篇文章主要介紹了IDEA之翻譯器的使用Translation,具有很好的參考價值,希望對大家有所幫助,如有錯誤或未考慮完全的地方,望不吝賜教
    2024-05-05
  • Jmeter中正則表達(dá)式提取器使用詳解

    Jmeter中正則表達(dá)式提取器使用詳解

    本文主要介紹了Jmeter中正則表達(dá)式提取器使用詳解,文中通過示例代碼介紹的非常詳細(xì),具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2021-11-11
  • Java 中的Printstream介紹_動力節(jié)點(diǎn)Java學(xué)院整理

    Java 中的Printstream介紹_動力節(jié)點(diǎn)Java學(xué)院整理

    PrintStream 是打印輸出流,它繼承于FilterOutputStream。接下來通過本文給大家介紹Java 中的Printstream,需要的朋友參考下吧
    2017-05-05
  • IDEA版使用Java操作Redis數(shù)據(jù)庫的方法

    IDEA版使用Java操作Redis數(shù)據(jù)庫的方法

    這篇文章主要介紹了IDEA版使用Java操作Redis數(shù)據(jù)庫的方法,首先需要下載jedis.jar包,然后再工程中設(shè)置具體操作步驟跟隨小編一起學(xué)習(xí)下吧
    2021-08-08
  • Java如何主動從當(dāng)前線程獲取異常信息

    Java如何主動從當(dāng)前線程獲取異常信息

    這篇文章主要介紹了Java如何主動從當(dāng)前線程獲取異常信息,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2022-10-10
  • Java源碼刨析之ArrayQueue

    Java源碼刨析之ArrayQueue

    在本篇文章當(dāng)中主要給大家介紹一個比較簡單的JDK為我們提供的容器ArrayQueue,這個容器主要是用數(shù)組實現(xiàn)的一個單向隊列,整體的結(jié)構(gòu)相對其他容器來說就比較簡單了
    2022-07-07
  • Java實現(xiàn)數(shù)字連連消

    Java實現(xiàn)數(shù)字連連消

    這篇文章主要為大家詳細(xì)介紹了Java實現(xiàn)數(shù)字連連消,文中示例代碼介紹的非常詳細(xì),具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2020-05-05
  • Java Fluent Mybatis實戰(zhàn)之構(gòu)建項目與代碼生成篇上

    Java Fluent Mybatis實戰(zhàn)之構(gòu)建項目與代碼生成篇上

    Java中常用的ORM框架主要是mybatis, hibernate, JPA等框架。國內(nèi)又以Mybatis用的多,基于mybatis上的增強(qiáng)框架,又有mybatis plus和TK mybatis等。今天我們介紹一個新的mybatis增強(qiáng)框架 fluent mybatis
    2021-10-10
  • 教你如何使用idea管理docker

    教你如何使用idea管理docker

    其實idea也提供了docker的管理功能,比如查看容器列表,啟動容器,停止容器等,本文來看下如何管理本地的docker?daemon和遠(yuǎn)程的dockers?daemon,感興趣的朋友跟隨小編一起看看吧
    2024-05-05

最新評論