MyBatis:控制对象创建与引用现有对象

时间:2011-11-04 17:49:13

标签: java mapping mybatis

这是我在这里的第一个问题,所以请告诉我是否有任何我可以提供的问题可以让我的问题更清晰。谢谢!

无论如何都要调整MyBatis(3.0.4),以便当它运行嵌套的结果映射并根据结果创建对象时,它不会创建“重复”对象,而是引用已经存在的对象产生的?为了澄清,假设我有一个由以下(简化)信息组成的对象:

Public class PrimaryObject {
    Private Contact role1;
    Private Contact role2;
    Private List<OtherObject> otherObjects;
}  

Public class OtherObject {
    Private String otherProperty;
    Private Contact otherRole;
}

结果map / SQL(假设类型别名):

<mapper namespace="PrimaryObject">
    <resultMap id="primaryObject" type="primaryObject">
        <association property="role1" column="ROLE_1_ID"
         select="Contact.findContactByPK" />
        <association property="role2" column="ROLE_2_ID"
         select="Contact.findContactByPK" />
        <collection property="otherObjects" column="PRIMARY_OBJECT_ID"
         javaType="List" ofType="OtherObject"
         select="OtherObject.findOtherObjectsByPrimaryObjectPK" />
    </resultMap>
    <select id="selectPrimaryObjectByPK" parameterType="..."
     resultMap="primaryObject">
        SELECT * FROM PRIMARY_OBJECT_TABLE
        WHERE PRIMARY_OBJECT_ID = #{value}
    </select>

...

<mapper namespace="OtherObject">
    <resultMap id="otherObject" type="otherObject">
        <result property="otherProperty" column="OTHER_PROPERTY" />
        <association property="otherRole" column="OTHER_ROLE_ID"
         select="Contact.findContactByPK" />
    </resultMap>
    <select id="findOtherObjectsByPrimaryObjectPK" parameterType="..."
     resultMap="otherObject">
        SELECT OTHER_OBJECT.OTHER_PROPERTY, OTHER_OBJECT.OTHER_ROLE_ID
        FROM OTHER_OBJECT JOIN PRIMARY_OBJECT
            ON PRIMARY_OBJECT.PRIMARY_OBJECT_ID = OTHER_OBJECT.PRIMARY_OBJECT_ID
    </select>

...

<mapper namespace="Contact">
    <resultMap id="contact" type="Contact">
        <result property...
        ...
    </resultMap>
    <select id="findContactByPK" parameterType="..." resultMap="contact">
        SELECT * FROM CONTACT...
    </select>

现在假设某个联系人在role1上同时充当role2primaryObject。从我所看到的情况来看,MyBatis创建了role1中引用的联系对象,当它到达role2时,它只是引用它为role1创建的对象。太棒了!

但是,假设同一个联系人充当otherRole中的otherObject。 MyBatis现在创建一个相同的联系对象,而不是在创建contact时引用创建/引用的原始primaryObject。有什么方法可以防止这种情况发生,而只是在我的otherObject中存储一个引用,该引用引用contactprimaryObject中的两个不同字段所指向的相同{{1}}?我一直在寻找一个custom ResultHandler,但是这个例子的复杂性加上我缺乏经验让我无法理解它是否能解决我想要解决的问题。提前感谢您的帮助和耐心!

1 个答案:

答案 0 :(得分:0)

好的,我认为您的问题可能与How to map a myBatis result to multiple objects?重复。所以,如果我理解正确的话,MyBatis没有本机支持这个问题。

您应该小心使用嵌套选择,因为它们在数据库上执行add select语句。我建议查看MyBatis 3 User Guide,特别是第35页及以上。 MyBatis有非常强大的方法来避免n + 1选择问题。 What is SELECT N+1?