一、前言


我们知道在resultMap中使用级联对于查找相关数据来说很方便(比如说查找雇员基本信息,顺便得到了雇员的体检信息、家庭信息、部门信息),但是有时我们不需要相关数据,那么在一些复杂的系统中,与主表相关联的表太多,一次查询执行多条无意义的SQL得到不需要的结果,就会浪费数据库的资源甚至对服务器的性能产生影响。为了应对这种问题MyBatis提供了延迟加载功能,即只执行所需信息的相关SQL。(类似Hibernate中,fetch="Lazy"时候的机制)

在mybatis-config的<settings>中有两个元素用来配置延迟加载:

<settings>
  <setting name="lazyLoadingEnabled" value="true|false"/>
  <setting name="aggressiveLazyLoading" value="true|false"/>
</settings>
配置项作用配置项说明默认值
lazyLoadingEnabled延迟加载的全局开关。当开启时,所有关联对象都会延迟加载。在特定关联关系中,可通过设置fetchType属性来覆盖该选项的开关状态。true|falsefalse
aggressiveLazyLoading当启用时,对任意延迟属性的调用会使(全部关联对象中,或者说同一层级)带有延迟加载属性的对象完整加载;反之,则每种属性按需加载。true|false

false

(3.4.1的版本之前默认true)

lazyLoadingEnabled:延迟加载的全局开关。当开启时所有关联对象(association、collection、discriminator)都具有了延迟属性。这时要看aggressiveLazyLoading是否开启

这两种属性搭配在一起共有三种情况:

  1. lazyLoadingEnabled为false:关闭延迟加载,这时就没有aggressiveLazyLoading的事了,任意查询会执行所有联级SQL,加载resultMap中全部联级对象。

  2. lazyLoadingEnabled为true:开启延迟加载,aggressiveLazyLoading为true,则对任意延迟属性调用都会执行同一层级的所有联级SQL,加载resultMap中全部联级对象。(感觉没什么卵用 = _ =)

  3. lazyLoadingEnabled为true:开启延迟加载,aggressiveLazyLoading为false,按需加载,比如说学生表中关联的家庭信息表和个人体检表,当你调用了体检表的属性只会执行resultMap中association中的select指定的SQL。

一般情况下都会采用第三种方式,配合级联元素(association、collection、discriminator)中的fetchType属性。

<collection property="employeeTaskList" column="id" select="mapper.EmployeeTaskMapper.getEmployeeTaskByEmpId" fetchType="eager"/>

fetchType有两个值:

  • eager,获取当前pojo后立即加载对应数据

  • lazy,获取当前pojo后延迟加载对应数据

当执行查询数据加载进主对象后继续执行fetchType值为eager的相关SQL并将数据加载进pojo

--------------------------------------------------------------------------------------------------

并不是很推荐这种级联查询的方式,除非它在所有的sql查询中都有需要。推荐的方法是写另外一个resultMap,extends原来的BaseResultMap,只在需要使用的sql中加入级联查询。

赞助本站,网站的持续发展离不开你们的支持!一分也是爱ヾ(◍°∇°◍)ノ゙
 本文链接: ,花了好多脑细胞写的,转载请注明链接喔~~
登陆
      正在加载评论