Hibernate缓存

原创 2012年03月26日 20:10:41

        Hibernate的缓存包括Session的缓存和SessionFactory的缓存,其中SessionFactory的缓存又可以分为两类:内置缓存和外置缓存。Session的缓存是内置的,不能被卸载,也被称为Hibernate的第一级缓存。SessionFactory的内置缓存和Session的缓存在实现方式上比较相似,前者是SessionFactory对象的一些集合属性包含的数据,后者是指Session的一些集合属性包含的数据。SessionFactory的内置缓存中存放了映射元数据和预定义SQL语句,映射元数据是映射文件中数据的拷贝,而预定义SQL语句是在Hibernate初始化阶段根据映射元数据推导出来,SessionFactory的内置缓存是只读的,应用程序不能修改缓存中的映射元数据和预定义SQL语句,因此SessionFactory不需要进行内置缓存与映射文件的同步。SessionFactory的外置缓存是一个可配置的插件在默认情况下,SessionFactory不会启用这个插件。外置缓存的数据是数据库数据的拷贝,外置缓存的介质可以是内存或者硬盘。SessionFactory的外置缓存也被称为Hibernate的第二级缓存。

Hibernate的缓存范围

       Hibernate的一级缓存和二级缓存都位于均位于持久层,且均用于存放数据库数据的副本,最大的区别就是缓存的范围各不一样.

存的范围分为3类:

1.事务范围
        事务范围的缓存只能被当前事务访问,每个事务都有各自的缓存,缓存内的数据通常采用相互关联的对象形式.缓存的生命周期依赖于事务的生命周期,只有当事务结束时,缓存的生命周期才会结束.事务范围的缓存使用内存作为存储介质,一级缓存就属于事务范围.
2.应用范围
        应用程序的缓存可以被应用范围内的所有事务共享访问.缓存的生命周期依赖于应用的生命周期,只有当应用结束时,缓存的生命周期才会结束.应用范围的缓存可以使用内存或硬盘作为存储介质,二级缓存就属于应用范围.
3.集群范围

        在集群环境中,缓存被一个机器或多个机器的进程共享,缓存中的数据被复制到集群环境中的每个进程节点,进程间通过远程通信来保证缓存中的数据的一致,缓存中的数据通常采用对象的松散数据形式.


Hibernate的二级缓存的配置
首先,不是所有的数据都适合放在二级缓存中,看一下,什么样的数据适合放在二级缓存中来?什么样的数据不适合放在二级缓存中来?

  下面这几种情况就
不适合加载到二级缓存中:
  1.经常被修改的数据
  2.绝对不允许出现并发访问的数据
  3.与其他应用共享的数据
  下面这己种情况
合适加载到二级缓存中:
  1.数据更新频率低
  2.允许偶尔出现并发问题的非重要数据
  3.不会被并发访问的数据
  4.常量数据
  5.不会被第三方修改的数据


Hibernate的二级缓存功能是靠配置二级缓存插件来实现的,Hibernate为了集成这些插件,Hibernate提供了org.hibernate.cache.CacheProvider接口,它充当缓存插件与Hibernate之间的适配器 .

常用的二级缓存插件
EHCache  org.hibernate.cache.EhCacheProvider
OSCache  org.hibernate.cache.OSCacheProvider
SwarmCahe  org.hibernate.cache.SwarmCacheProvider
JBossCache  org.hibernate.cache.TreeCacheProvider

数据放入缓存:

1. save()。当session对象调用save()方法保存一个对象后,该对象会被放入到session的缓存中。

2. get()和load()。当session对象调用get()或load()方法从数据库取出一个对象后,该对象也会被放入到session的缓存中。

3. 使用HQL和QBC等从数据库中查询数据。


hibernate.jdbc.batch_size:hibernate每次提交的sql语句数量。将多条语句一起提交,而不是单独提交以获得性能上的提高。

hibernate.jdbc.fetch_size:每次取出的数据量。


Hibernate查询缓存缓存的是查询出来的实体的部分属性结果集和实体的ID (注意这里不是实体)


hibernate的n+1问题:

1)使用懒加载

2)在*.hbm.xml中,使用fetch="join",这样hibernate会使用外连接来加载器关联实体。不过这样会让懒加载失效。


在hibernate中,update是会将数据放在缓存中的。当select的时候,也是先在缓存中查找的(此时数据库还没有做update操作)。当session关闭的时候,缓存中的数据会自动清空。此时,update操作才会发射到数据库中。

查询操作中list和iterate的区别:

1)list每次都发射sql。list会向缓存中放入数据,但是不会利用缓存

2)iterate会利用缓存。



Transient状态的对象的特性?
* 在数据库中没有与之匹配的记录
* 没有纳入session的管理

persistent状态的对象的特性?
* 纳入session的管理
* persistent状态的对象在数据库中存在与之匹配的数据
* persistent状态的对象在清理缓存(脏数据检查),会和数据库同步

detached状态的对象的特性?
* 在数据库中存在与之对应的记录
* 没有纳入session的管理

session.flush方法主要做两件事:
* 清理缓存
* 执行sql

session在什么情况下执行flush
* 默认在事务提交时
* 显示调用flush
* 在执行查询前,如:iterate

Hibernate级联保存要如何做?

Inverse是hibernate双向关系中的基本概念。inverse的真正作用就是指定由哪一方来维护之间的关联关系。当一方中指定了“inverse=false”(默认),那么那一方就有责任负责之间的关联关系,说白了就是hibernate如何生成Sql来维护关联的记录。


Hibernate延迟加载的机制是什么,如何工作?

延迟加载机制是为了避免一些无谓的性能开销而提出来的,所谓延迟加载就是当在真正需要数据的时候,才真正执行数据加载操作。在Hibernate中提供了对实体对象的延迟加载以及对集合的延迟加载,另外在Hibernate3中还提供了对属性的延迟加载。

实体的延迟加载:

<class name=”com.neusoft.entity.User” table=”user” lazy=”true”>
集合类型的延迟加载:
<hibernate-mapping>

    <class name=”com.neusoft.entity.User” table=”user”>

…..

<set name=”addresses” table=”address” lazy=”true” inverse=”true”>

<key column=”user_id”/>

<one-to-many class=”com.neusoft.entity.Arrderss”/>

</set>

    </class>

</hibernate-mapping>
属性延迟加载:
<property name=”resume” type=”java.sql.Clob” column=”resume” lazy=”true”/>

集合延迟加载的原理看这里。讲述了hibernate如何通过代理模式来实现延迟加载(需要的时候再去取数据)。hibernate自己实现了Set、List、Map类型,并且在set中保存了session对象和集合的owner。如下图:


当延迟加载需要访问set的时候,根据owner中的外键去相应的表中查询外间关联的数据。

熟悉 Hibernate 集合属性读者应该记得:Hibernate 要求声明集合属性只能用 Set、List、Map、SortedSet、SortedMap 等接口,而不能用 HashSet、ArrayList、HashMap、TreeSet、TreeMap 等实现类,其原因就是因为 Hibernate 需要对集合属性进行延迟加载,而 Hibernate 的延迟加载是依靠 PersistentSet、PersistentList、PersistentMap、PersistentSortedMap、PersistentSortedSet 来完成的——也就是说,Hibernate 底层需要使用自己的集合实现类来完成延迟加载,因此它要求开发者必须用集合接口、而不是集合实现类来声明集合属性。延迟的关联实体将是一个动态生成代理对象。只要应用程序需要使用“暂未加载”的关联实体,Person_$$_javassist_0 代理对象会负责去加载真正的关联实体,并返回实际的关联实体——这就是最典型的代理模式。


对Hibernate缓存的理解

Hibernate的缓存目前比较常见的使用是它的:一级缓存(Session缓存),二级缓存(第三方插件缓存)。 缓存:          缓存就是把当前查询出来或是使用过的对象保存到内存中(一个数...
  • gst6062825
  • gst6062825
  • 2012年05月16日 18:05
  • 475

Hibernate的N+1问题与缓存机制讲解

在面试的过程中我对源码深度的掌握不够,所以对这个问题还是比较有深刻的感触。偶然看见别人写的解释特记录说明下。 一、N+1问题 首先我们来探讨一下N+1的问题,我们先通过一个例子来看一下...
  • fjnpysh
  • fjnpysh
  • 2017年03月10日 00:13
  • 382

hibernate中的缓存的分类及执行过程

hibernate是一个线程对应一个session,一个线程可以看成一个用户。也就是说session级缓存(一级缓存)只能给一个线程用,别的线程用不了,一级缓存就是和线程绑定了。 hibernate一...
  • Android_MSK
  • Android_MSK
  • 2017年04月06日 20:12
  • 334

Hibernate常用的缓存插件及其使用

Hibernater 的二级缓存是一个插件,下面是几种常用的缓存插件: l EhCache:可作为进程范围的缓存,存放数据的物理介质可以是内存或硬盘,对Hibernate的查询缓存提供了支持。 l...
  • huazaichang
  • huazaichang
  • 2013年01月29日 13:50
  • 1396

Hibernate旅程(八)Hibernate缓存机制--二级缓存

Hibernate二级级缓存 上篇介绍了Hibernate一级缓存,主要是session缓存,session生命周期结束,缓存也就结束。二级缓存相对于一级缓存来说是一个范围更广阔一些,就比你住的地...
  • lovesummerforever
  • lovesummerforever
  • 2014年03月13日 10:51
  • 3630

hibernate 缓存应用概述

Hibernate是一个ORM框架,由于现在多数web应用工作在并发环境中,为了减少应用程序对数据服务器的频繁访问,减少对数据库服务器的形成高负荷。通常需要在web应用中使用缓存机制。这种情况下,Hi...
  • lkx94
  • lkx94
  • 2014年11月30日 23:48
  • 507

Hibernate缓存和加强

Hibernate缓存和加强 懒加载     懒加载(Load On Demand)是一种独特而又强大的数据获取方法 ,是指程序推迟访问数据库,这样做可以保证有时候不必要的访问数据库,因为...
  • q547550831
  • q547550831
  • 2016年02月15日 18:52
  • 1445

HIbernate缓存

  • vastskyjoe
  • vastskyjoe
  • 2009年01月07日 21:15
  • 598

Hibernate缓存

1、Hibernate缓存概述        缓存是介于物理数据源与应用程序之间,是数据库数据在内存中的 存放临时copy的容器,        其作用是为了减少应用程序对物理数据源访问的次数,从而...
  • zd8582zd
  • zd8582zd
  • 2010年07月22日 19:21
  • 241

Hibernate之缓存详解

一,缓存的概念 二,缓存的范围 三,Hibernate中的第一级缓存 1,get查询测试: 1>在同一个session中发出两次get查询 public void Query(){ Sessio...
  • an_2016
  • an_2016
  • 2016年08月03日 21:57
  • 21088
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:Hibernate缓存
举报原因:
原因补充:

(最多只允许输入30个字)