iBatis如何解决更复杂的N + 1问题

时间:2010-06-03 19:18:52

标签: sql ibatis

我有一个类似于以下内容的数据库:

create table Store(storeId)
create table Staff(storeId_fk, staff_id, staffName)
create table Item(storeId_fk, itme_id, itemName)

商店表很大。

我创建了以下java bean

public class Store
{
    List<Staff> myStaff
    List<Item> myItem

   ....
}

public class Staff
{
    ...
}

public class Item
{
   ...
}

我的问题是我如何使用iBatis的结果图来高效地从表格映射到java对象?

我试过了:

<resultMap id="storemap" class="my.example.Store">
  <result property="myStaff" resultMap="staffMap"/>
  <result property="myItem" result="itemMap"/>
</resultMap>

(other maps omitted)

但由于Store表非常大,所以速度太慢了。

我试图按照Clinton的N + 1解决方案开发者指南中的示例进行操作,但我无法围绕如何将“groupBy”用于具有2个列表的对象...

感谢任何帮助!

1 个答案:

答案 0 :(得分:1)

当您开始想要加载对象图时,您就会开始理解为什么iBatis不是ORM,只是一个对象映射器。你是对的,使用iBatis的groupBy功能在映射中加载关系(避免N + 1问题)的方法很难概括为你的场景。我认为可以做到,但我不会打扰。

通常在这里实现一些延迟加载,或者显式加载相关对象。 无论如何,我不确定你的目标是什么。你说“商店桌非常大”。 现在,您打算加载许多Store对象吗?你真的需要相关的物品吗? 问问自己(在使用iBatis进行设计时)要执行的理想SQL是什么。

并且不要忘记处理对象可能有不同的场景,并且不一定所有场景都必须使用相同的映射。

例如,通常有一种与Store对象相关的用例类型:在第一种类型中,一种需要加载完整的“对象图”,但仅需要加载一个(或几个)根对象(一个{{ 1}});在另一种类型中,必须加载许多“商店”(带有相关数据),但仅用于某些列表或报告。然后,你可以对每种情况做不同的事情:第一种,用相关对象加载完整对象(可能是延迟加载,而不用担心N + 1问题);在第二个,一个并没有真正加载完整的Store对象图,而只是一些虚拟Store DTO对象(可能甚至是一个简单的HashMap!),它对应于列表的一行 - 而且可以实现这一点在iBatis中,使用临时SQL查询和映射。