一、延迟载入定义

        
       延迟载入,也叫懒载入,它是Hibernate为提高程序运行效率而提供的一种机制,即当仅仅有真正使用该对象的数据时才会创建。

说白了,所谓的延迟载入不是在load的时候去数据库载入数据。而是当我在应用程序中真正使用该数据时Hibernate才去查询、载入对应的数据。


二、延迟载入实现原理

        
       Hibernate中主要是通过代理(proxy)机制来实现延迟载入。即Hibernate丛数据库获取某一个对象数据时、获取某一 个对象的集合属性值时。或获取某一个对象所关联的还有一个对象时。因为没有使用该对象的数据。hibernate并非数据库载入真正的数据,而仅仅是为该对 象创建一个代理对象来代表这个对象。这个对象上的全部属性都是默认值;仅仅有在真正须要使用该对象的数据时才创建这个真实对象,真正从数据库中载入它的数据。
       如:
      User user=(User)session.load(clazz, id);
      System.out.println(user.getId());
      user.getName();
      运行前两句代码时直接返回的是代理对象,没有发送sql语句到数据库载入。这样生成的代理对象具有与真实对象同样的属性和方法,仅仅是在实例化的时候仅仅实例化了该对象的id,当真正使用该对象的其它属性和方法时(运行第三句代码),才创建真实的User实例,并发送sql语句到数据库中载数据,这样大大节省了内存。
 

三、延迟载入应用环境

       
        当我们要訪问的数据量过大时。明显用缓存不太合适, 由于内存容量有限 。为了降低并发量。降低系统资源的消耗,这时Hibernate用懒载入机制来弥补这样的缺陷,可是这仅仅是弥补而不是用了懒载入整体性能就提高了。
       

实现懒载入的条件:

       
       1 实体类不能是final的 
       2 能实现懒载入的对象都是被CGLIB(反射调用)改写的代理对象,所以不能是final修饰的
       3 需要asm,cglib两个jar包
       4 对应的lazy属性为true
       5 对应的fetch属性为select 

Hibernate实现的懒载入:


1、   通过Session.load()实现懒载入
       load(Object, Serializable):依据id查询 。查询返回的是代理对象。不会立马訪问数据库,是懒载入的。当真正去使用对象的时候才会訪问数据库。

      使用load()时假设在session关闭之后再查询此对象,会报异常:could not initialize proxy - no Session。处理办法:
      a.在session关闭之前初始化一下查询出来的对象:Hibernate.initialize(user);
      b.在web.xml中配置OpenSessionInView过滤器就可以解决
<!-- OpenSessionInView 配置。解决Hibernate延迟载入的问题 -->
  <filter>
   <filter-name>lazyLoadingFilter</filter-name>
   <filter-class>org.springframework.orm.hibernate3.support.OpenSessionInViewFilter</filter-class>
  </filter>
 
<filter-mapping>
   <filter-name>lazyLoadingFilter</filter-name>
   <url-pattern>*.do</url-pattern>
  </filter-mapping>

2、   one-to-one(元素)实现了懒载入。

       在一对一的时候,查询主对象时默认不是懒载入。

即:查询主对象的时候也会把从对象查询出来。须要把主对象配制成lazy="true" constrained="true"  fetch="select"。此时查询主对象的时候就不会查询从对象。从而实现了懒载入。

 
3、   many-to-one(元素)实现了懒载入。
       多对一的时候,查询主对象时默认是懒载入。即:查询主对象的时候不会把从对象查询出来。多对一的时候,查询从对象时默认是懒载入。

即:查询从对象的时候不会把主对象查询出来。

       hibernate3.0中lazy有三个值,true。false,proxy,默认的是lazy="proxy".详细设置成什么要看你的需求。并非说哪个设置就是最好的。在<many-to-one>与<one-to-one>标签上:当为true时,会有懒载入特性,当为false时会产生N+1问题,比方一个学生相应一个班级,用一条SQL查出10个学生,当訪问学生的班级属性时Hibernate会再产生10条SQL分别查出每一个学生相应的班级.
fetch= 捉取方式:select=关联查询;join=连接表的方式查询(效率高),fetch=join时,lazy的设置将没有意义.
 
4、   one-to-many(元素)懒载入:默认会懒载入,这是必须的,是重经常使用的。

        一对多的时候。查询主对象时默认是懒载入。

即:查询主对象的时候不会把从对象查询出来。

须要配置主对象中的set集合lazy="false" 这样就配置成是不懒载入了。或者配置抓取方式fetch="join"也能够变成不懒载入。

 

四、总结

       
       依据以上总结我们发现,在Hibernate的延迟载入机制中,大部分是针对集合类型(关联映射设置多的一方延迟载入)的应用意义最为重大。由于这有可能使性能得到大幅度的提高。而Hibernate 的延迟载入(lazy load)本质上就是代理模式的应用。通过代理模式来减少系统的内存开销、提升应用的执行性能。Hibernate 充分利用了代理模式的这样的优势,并结合了 Javassist 或 CGLIB 来动态地生成代理对象。这更加添加了代理模式的灵活性。仅仅只是Hibernate 给这样的使用方法一个新名称:延迟载入。

不管怎样,分析、了解这些开源框架的实现能够更好的体会到这些经典设计模式的优势所在。



Hibernate 延迟载入的更多相关文章

  1. Hibernate中的session和load延迟载入矛盾问题,怎样解决?

    假设延迟载入出现session close的情况下 方法1.在web.xml中配置spring的openSessionInViewFilter <filter>  <filter-n ...

  2. hibernate 普通字段延迟载入无效的解决的方法

    关联对象的延迟载入就不说了.大家都知道. 关于普通字段的延迟载入,尤其是lob字段,若没有延迟载入,对性能影响极大.然而简单的使用 @Basic(fetch = FetchType.LAZY) 注解并 ...

  3. hibernate之4.延迟载入

    延迟载入: 仅仅有当使用以实体对象的属性(除主键属性外)时,才会发送查询语句到数据库 get不支持延迟载入 @Test public void getTest(){ Session session=n ...

  4. 50个Android开发技巧(02 延迟载入和避免反复渲染视图)

    当你在Application中创建复杂的布局时.页面的渲染过程也变得更加缓慢. 此时,我们须要利用 <include />标签(避免反复渲染)和 ViewStub类(延迟载入)来优化我们的 ...

  5. 原声JS瀑布流加延迟载入

    <!doctype html> <html lang="en"> <head> <meta charset="UTF-8&quo ...

  6. 延迟载入Dll(动态载入Dll)

    windows核心编程(第五版)20.3节的延迟载入Dll 延迟载入Dll技术出现的原因: 因为DLL的加载是比较浪费时间的,特别是大型软件加载,因此,这项技术是在应对软件初始化过程中避免浪费太多的时 ...

  7. 【java】itoo项目实战之hibernate 懒载入优化性能

    在做itoo 3.0 的时候,考评系统想要上线,就開始导入数据了,仅仅导入学生2万条数据,可是导入的速度特别的慢.这个慢的原因是由于导入的时候进行了过多的IO操作.可是导入成功之后,查询学生的速度更加 ...

  8. Hibernate 学习教程

    第1课 课程内容. 6 第2课Hibernate UML图. 6 第3课 风格. 7 第4课 资源. 7 第5课 环境准备. 7 第6课 第一个演示样例HibernateHelloWorld 7 第7 ...

  9. Java面试-Hibernate总结

    1  Hibernate的检索方式 Ø  导航对象图检索(依据已经载入的对象.导航到其它对象. ) Ø  OID检索(依照对象的OID来检索对象. ) Ø  HQL检索(使用面向对象的HQL查询语言. ...

随机推荐

  1. FastReport.Net使用:[19]复选框的使用

    FastReport中,用好复选框会使报表更美观. 复选框的用法举例: 1.点菜系统中,打印用户点菜时,将已点的菜进行打“√”标记等. 2.选课系统中,将已选科目进行打“√”等. 认识复选框 复选框只 ...

  2. 【BZOJ 1566】 1566: [NOI2009]管道取珠 (DP)

    1566: [NOI2009]管道取珠 Time Limit: 20 Sec  Memory Limit: 650 MBSubmit: 1659  Solved: 971 Description In ...

  3. 【BZOJ 3958】 3958: [WF2011]Mummy Madness (二分+扫描线、线段树)

    3958: [WF2011]Mummy Madness Time Limit: 10 Sec  Memory Limit: 256 MBSubmit: 96  Solved: 41 Descripti ...

  4. 「CSA49」Bunny on Number Line

    「CSA49」Bunny on Number Line 题目大意:有一个人从0开始走,每次可以向前走一步或者回到1,那么会产生一个位置序列,其中给出 \(k\) 个位置是好的.定义一个位置序列是好的, ...

  5. 【欧拉函数】BZOJ4173-数学

    [题目大意] [思路] 基本是popoqqq大爷的题解,稍微添加了几句自己的注释,方便理解 同理,如果n%k+m%k<k等价于0 =∑([(n+m)/k]-[n/k]-[m/k])×φ(k) … ...

  6. hibernate核心及常用技术

    一.hibernate介绍 1.hibernate概述 hibernate是轻量级Java EE持久层解决方案,管理java类到数据库表的映射(ORM:对象关系型数据映射),并提供数据查询获取的方法. ...

  7. JNI介绍

    JNI是在学习Android HAL时必须要面临一个知识点,如果你不了解它的机制,不了解它的使用方式,你会被本地代码绕的晕头转向,JNI作为一个中间语言的翻译官在运行Java代码的Android中有着 ...

  8. bzoj1001: [BeiJing2006]狼抓兔子 -- 最小割

    1001: [BeiJing2006]狼抓兔子 Time Limit: 15 Sec  Memory Limit: 162 MB Description 现在小朋友们最喜欢的"喜羊羊与灰太狼 ...

  9. noip200806火柴棒等式

    试题描述: 给你n根火柴棍,你可以拼出多少个形如“A+B=C”的等式?等式中的A.B.C是用火柴棍拼出的整数(若该数非零,则最高位不能是0).用火柴棍拼数字0-9的拼法如图所示: 注意: 1)加号与等 ...

  10. Mac下配置Idea的Maven

    环境版本: Mac OS: 10.13.4 JDK: 1.8 Idea: 2018.3 Maven: 3.6.0 Maven 相关配置: Maven 下载: http://maven.apache.o ...