需求:
我们查询所有的员工列表,然后根据员工的部门编号查询对应的部门信息
如何解决
方式一:连接查询。一条SQL语句查询出所有的信息
方式二: 延迟加载。关联表的数据只有在真正使用的时候才去查询,不使用不查询。
优点
先从单表查询,需要时再从关联表去关联查询,大大提高了数据库的性能,因为单表查询要比关联查询多张表速度要快。
配置方法
延迟加载多用在关联对象和集合中,association和collection具备设置延迟加载的功能
设置全局开关
在mybatis-config.xml中打开延迟加载的开关。配置完成后,所有的association和collection元素都生效
<settings><!--开启全局的懒加载--><settingname="lazyLoadingEnabled"value="true"/><!--是否立即加载,其实不用配置,默认为false--><settingname="aggressiveLazyLoading"value="falsec"/></settings>
lazyLoadingEnabled | MyBatis是否开启延迟加载的总开关,当开启时,所有关联对象都会延迟加载。特定关联关系中,可通过设置fetchType属性来覆盖该项的开关状态 | true /false | false |
aggressiveLazyLoading | 开启时,任一方法的调用都会加载该对象的所有延迟加载属性。否则,每个延迟加载属性会按需加载 | true /false | false 在 3.4.1 及之前的版本默认值为 true |
配置单项开关
在指定的association和collection元素中配置fetchType属性。该属性配置将覆盖全局延迟设置.
eager | 立即加载 |
lazy | 延迟加载 |
代码实现
用户类及账户类
publicclassUserimplementsSerializable{ privateIntegerid; privateStringusername; privateDatebirthday; privateStringsex; privateStringaddress; privateList<Account>accountList; get和set方法省略..... } publicclassAccountimplementsSerializable{ privateIntegerid; privateIntegeruid; privateDoublemoney; get和set方法省略..... }
Mapper.java
publicinterfaceUserMapper { /*** 查询所有的用户*/List<User>findAll(); } publicinterfaceAccountMapper { /*** 根据用户ID查询账户信息* @return*/List<Account>findAllByUid(Integeruid); }
Mapper.xml文件
userMapper.xml
<resultMapid="userAccountMap"type="com.example.domain.User"><idproperty="id"column="id"/><resultproperty="username"column="username"/><resultproperty="birthday"column="birthday"/><resultproperty="sex"column="sex"/><resultproperty="address"column="address"/><collectionproperty="accountList"ofType="com.example.domain.Account"column="id"select="com.example.dao.AccountDao.findAllByUid"/></resultMap><selectid="findAll"resultMap="userAccountMap"> SELECT * FROM USER; </select>
accountMapper.xml
<selectid="findAllByUid"resultType="com.example.domain.Account"> SELECT * FROM account WHERE uid = #{uid}; </select>
注意:
通过懒加载查询完数据后,只需要确定SQL语句是否查询了对应的关联表即可。不要输出对象,否则相当于使用了对象,就会进行对应的关联查询。