一、Mybatis的级联映射
使用Mybatis的级联映射,我们可以轻松的实现一对一、一对多或者多对多关联查询,甚至可以利用级联映射实现懒加载。
所谓的懒加载,就是我们在一个实体对象中关联了其他对象,如果不需要获取被关联的对象,则不会对被关联的实体执行额外的查询操作,仅在使用get方法获取被关联对象时才会执行该对象的查询操作。通过这种方式可以一定程度上减轻数据库的压力。
下面我们先讲讲级联映射的应用:
1、准备工作
2、一对多关联映射
3、一对一关联映射
4、Discriminator
二、懒加载机制
分步查询的类型才能使用懒加载,而join方式则用不了。assication、collection具备延迟加载功能
三、Mybatis级联映射实现原理
1、ResultMap详解
ResultMap是实现级联映射和懒加载的基础,所以在介绍源码前,先对ResultMap进行了解。
ResultMap的解析流程:
mybatis启动时,会将所有配置信息转化为java对象,通过<resultMap>标签配置的信息也一样,Mybatis通过ResultMap类描述<resultMap>标签的配置信息,ResultMap类的所有属性如下:
知道ResultMap类各属性的作用后,我们来了解一下<resultMap>标签解析生成ResultMap对象的过程:
前面我们说过,Mybatis配置信息的解析是通过XMLMapperBuilder类完成的, 该类提供了一个parse方法,该方法会解析Mapper中的所有配置信息,代码如下:
进行configurationElement方法:
进入ResultMapElements方法:
如上面所示,首先会先获取<resultMap>标签的所有属性信息,然后对<constructor>、<discriminator>子标签进行解析,然后创建一个ResultMapResolver对象,调用该对象的resolve方法放回一个ResultMap对象,resolve方法的代码如下:
该代码中就是调用了MapperBuilderAssistant对象的addResultMap方法进行创建了ResultMap对象,并把ResultMap对象添加到Configuration对象中,addResultMap方法的代码如下:
该方法中先判断ResultMap是否继承了其他ResultMap对象,如果是,则将父RessultMap的构造映射信息去掉并将父ResultMap中配置的映射信息添加到子ResultMap对象中,最后通过建造者模式创建ResultMap对象。在ResultMap.Builder类中创建一个ResultMap对象,然后为ResultMap对象得的所以属性赋值。
2、级联映射实现原理
之前介绍Mybatis的核心组件的时候提过,StatementHandler组件与数据库完成交互后,会使用ResultHandler组件对结果集进行处理,我们以PreparedStatementHandler类的query方法来看看这个过程:
ResultSetHandler接口只有一个默认的实现,即DefaultResultSetHandler类,该类中handleResultSets方法实现如下:
四、懒加载实现原理
aaaaa