Mybatis延迟加载

1、延迟加载概述

  1. 应用场景 如果查询订单并且关联查询用户信息。如果先查询订单信息即可满足要求,当我们需要查询用户信息时再查询用户信息。把对用户信息的按需去查询就是延迟加载。
  2. 延迟加载的好处 先从单表查询、需要时再从关联表去关联查询,大大提高 数据库性能,因为查询单表要比关联查询多张表速度要快。
  3. 延迟加载的条件:1)resultMap可以实现高级映射(使用association、collection实现一对一及一对多映射),association、collection具备延迟加载功能。2)延迟加载是针对分步查询而言的

2、开启延迟加载

Mybatis的延迟加载功能默认是关闭的

需要在mybatis-config.xml全局配置文件中通过setting标签配置来开启延迟加载功能

需要在mybatis-config.xml全局配置文件中通过setting标签配置来开启延迟加载功能开启延迟加载的属性:

lazyLoadingEnabled:全局性设置懒加载。默认为false,true表示开启延迟加载
aggressiveLazyLoading:false表示关闭积极加载
说明:这两个属性必须一起设置

【示例】

<settings>
     <!--开启延迟加载-->
     <setting name="lazyLoadingEnabled" value="true"/>
     <!--关闭积极加载-->
     <setting name="aggressiveLazyLoading" value="false"/>
 </settings>

3、延迟加载测试

延迟加载需求:通过订单编号20140921003查询order并延迟加载user。就是演示上述演示过的一对一的表关系案例。

如果通过订单编号查询order并且查询user信息,在正常情况下的查询语句应该是:

分析:

如果改成延迟加载,也就意味着,先查询order,等需要的时候再去查询user,那就相当于将上面的一条语句变成了两条语句:

1、通过订单编号查询order

2、通过查询出来的order中的user_id查询user

sql语句:

分步查询:
    #第一步:根据order_number查询订单信息;
    SELECT * FROM tb_order WHERE order_number = '20140921003';
    #第二步:根据订单信息中的user_id查询出下单人的信息;
    SELECT * FROM tb_user WHERE id = 1;
第一步:编写接口方法

在OrderMapper接口中新建:queryOrderUserLazy方法

    /**
     * 根据orderNumber懒加载查询订单及用户信息
     * @param orderNumber
     * @return
     */
    Order queryOrderUserLazy(@Param("orderNumber") String orderNumber);
第二步:编写SQL

【OrderMapper.xml】

 <!--懒加载结果集-->
    <resultMap id="orderUserLazyResultMap" type="Order">
        <id property="id" column="id"/>
        <!--
             1.column属性:延迟加载的sql语句中所需的参数,就是SELECT * FROM tb_user WHERE id = ?;
             该sql语句的?位置。这里书写 user_id因为执行  SELECT * FROM tb_order WHERE order_number = #{orderNumber} 语句查询的用户id对应的列名就是user_id

             2.select属性:调用指定sql语句来执行延迟加载,就是指定sql语句所在的位置,根据用户id查询用户信息位于UserMapper.xml文件中,具体地址是:namespace.id
             3.执行流程:
                先执行SELECT * FROM tb_order WHERE order_number = #{orderNumber} 根据订单号获取订单信息(包括用户id)
                然后根据 select="com.itheima.sh.dao.UserMapper.selectById" 找到UserMapper.xml文件中的:
                    <select id="selectById" resultType="User">
                        select * from tb_user where id = #{id}
                    </select>

              并将column="user_id" 对应的列值传递过去
              并将查询的结果封装到User对象中,最后将User对象封装到Order对象中
          -->
        <association property="user" javaType="User" column="user_id"  select="com.itheima.sh.dao.UserMapper.selectById"></association>

    </resultMap>

    <select id="queryOrderUserLazy" resultMap="orderUserLazyResultMap">
        SELECT * FROM tb_order WHERE order_number = #{orderNumber}
    </select>

【UserMapper.xml】

<mapper namespace="com.itheima.sh.dao.UserMapper">
    <!--
    查询语句
    id: 接口中方法的名字
    resultType:返回的实体类的类型,类全名
    -->
    <select id="selectById" resultType="User">
        select * from tb_user where id = #{id}
    </select>


</mapper>

说明:

1.column属性:延迟加载的sql语句中所需的参数,就是SELECT * FROM tb_user WHERE id = ?; 该sql语句的?位置。这里书写 user_id因为执行 SELECT * FROM tb_order WHERE order_number = #{orderNumber} 语句查询的用户id对应的列名就是user_id 2.select属性:调用指定sql语句来执行延迟加载,就是指定sql语句所在的位置,根据用户id查询用户信息位于 UserMapper.xml文件中,具体地址是:namespace.id 3.执行流程: 先执行SELECT * FROM tb_order WHERE order_number = #{orderNumber} 根据订单号获取订单信息(包括用户id) 然后根据 select="com.itheima.sh.dao.UserMapper.selectById" 找到UserMapper.xml文件中的: select * from tb_user where id = #{id} 并将column="user_id" 对应的列值传递过去 并将查询的结果封装到User对象中,最后将User对象封装到Order对象中

【注意】

  1. 懒加载首先是把SQL拆分;
  2. 然后在resultMap中,通过关联映射配置中的,select属性引入需要懒加载进来的对象;
第三步:开启懒加载

在mybatis-config.xml全局配置文件中,开启懒加载

    <!--settings属性配置-->
    <settings>
        <!--开启延迟加载-->
        <setting name="lazyLoadingEnabled" value="true"/>
        <!--关闭积极加载-->
        <setting name="aggressiveLazyLoading" value="false"/>
    </settings>
第四步:测试

【没有访问关联对象】

在没有访问关联对象的属性时,只发送了一条SQL。

【访问关联对象的属性】

访问关联对象属性时,发送了两条SQL语句。按需查询-----懒加载!

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值