Hibernate缓存总结.docx
《Hibernate缓存总结.docx》由会员分享,可在线阅读,更多相关《Hibernate缓存总结.docx(26页珍藏版)》请在冰点文库上搜索。
Hibernate缓存总结
ehcache和hibernate集成的时候是这么配置的:
org.hibernate.cache.EhCacheProvider
/ehcache.xml
true
ehcache和spring集成的时候是这么配置的:
classpath:
ehcache.xml
Ehcache与oscache区别:
ehcache主要是对数据库访问的缓存,相同的查询语句只需查询一次数据库,从而提高了查询的速度
oscache主要是对页面的缓存,可以整页或者指定网页某一部分缓存,同时指定他的过期时间,这样在此时间段里面访问的数据都是一样的
hibernate2以前提倡用ehcache
hibernate3后提倡oscache,
(一)一级缓存(一级缓存是缓存实体对象的,不缓存普通属性,session范围内)
publicclassCacheLevel1TestextendsTestCase{
/**
*在同一个session中发出两次load查询
*/
publicvoidtestCache1(){
Sessionsession=null;
try{
session=HibernateUtils.getSession();
session.beginTransaction();
Studentstudent=(Student)session.load(Student.class,1);
System.out.println("student.name="+student.getName());
//不会发出sql,因为load使用缓存(默认事务范围缓存一级缓存)
student=(Student)session.load(Student.class,1);
System.out.println("student.name="+student.getName());
session.getTransaction().commit();
}catch(Exceptione){
e.printStackTrace();
session.getTransaction().rollback();
}finally{
HibernateUtils.closeSession(session);
}
}
/**
*在同一个session中发出两次get查询
*/
publicvoidtestCache2(){
Sessionsession=null;
try{
session=HibernateUtils.getSession();
session.beginTransaction();
Studentstudent=(Student)session.get(Student.class,1);
System.out.println("student.name="+student.getName());
//不会发出sql,因为get使用缓存
student=(Student)session.get(Student.class,1);
System.out.println("student.name="+student.getName());
session.getTransaction().commit();
}catch(Exceptione){
e.printStackTrace();
session.getTransaction().rollback();
}finally{
HibernateUtils.closeSession(session);
}
}
/**
*在同一个session中发出两次iterate查询实体对象
*/
publicvoidtestCache3(){
Sessionsession=null;
try{
session=HibernateUtils.getSession();
session.beginTransaction();
Studentstudent=(Student)session.createQuery("fromStudentswheres.id=1").iterate().next();
System.out.println("student.name="+student.getName());
//会发出查询id的sql,不会发出查询实体对象的sql,因为iterate使用缓存
student=(Student)session.createQuery("fromStudentswheres.id=1").iterate().next();
System.out.println("student.name="+student.getName());
session.getTransaction().commit();
}catch(Exceptione){
e.printStackTrace();
session.getTransaction().rollback();
}finally{
HibernateUtils.closeSession(session);
}
}
/**
*在同一个session中发出两次iterate查询实体对象
*/
publicvoidtestCache4(){
Sessionsession=null;
try{
session=HibernateUtils.getSession();
session.beginTransaction();
Stringname=(String)session.createQuery("selects.namefromStudentswheres.id=1").iterate().next();
System.out.println("student.name="+name);
//iterate查询普通属性,一级缓存不会缓存,所以发出sql
//一级缓存是缓存实体对象的
name=(String)session.createQuery("selects.namefromStudentswheres.id=1").iterate().next();
System.out.println("student.name="+name);
session.getTransaction().commit();
}catch(Exceptione){
e.printStackTrace();
session.getTransaction().rollback();
}finally{
HibernateUtils.closeSession(session);
}
}
/**
*开启两个session中发出load查询
*/
publicvoidtestCache5(){
Sessionsession=null;
try{
session=HibernateUtils.getSession();
session.beginTransaction();
Studentstudent=(Student)session.load(Student.class,1);
System.out.println("student.name="+student.getName());
session.getTransaction().commit();
}catch(Exceptione){
e.printStackTrace();
session.getTransaction().rollback();
}finally{
HibernateUtils.closeSession(session);
}
try{
session=HibernateUtils.getSession();
session.beginTransaction();
//会发出查询语句,session间不能共享一级缓存的数据
//因为它会伴随session的生命周期存在和消亡
Studentstudent=(Student)session.load(Student.class,1);
System.out.println("student.name="+student.getName());
session.getTransaction().commit();
}catch(Exceptione){
e.printStackTrace();
session.getTransaction().rollback();
}finally{
HibernateUtils.closeSession(session);
}
}
/**
*在同一个session中先save,在发出load查询save过的数据
*/
publicvoidtestCache6(){
Sessionsession=null;
try{
session=HibernateUtils.getSession();
session.beginTransaction();
Studentstu=newStudent();
stu.setName("王五");
Serializableid=session.save(stu);
//不会发出sql,因为save是使用缓存的
Studentstudent=(Student)session.load(Student.class,id);
System.out.println("student.name="+student.getName());
session.getTransaction().commit();
}catch(Exceptione){
e.printStackTrace();
session.getTransaction().rollback();
}finally{
HibernateUtils.closeSession(session);
}
}
/**
*向数据库中批量加入1000条数据
*/
publicvoidtestCache7(){
Sessionsession=null;
try{
session=HibernateUtils.getSession();
session.beginTransaction();
for(inti=0;i<1000;i++){
Studentstudent=newStudent();
student.setName("s_"+i);
session.save(student);
//每20条数据就强制session将数据持久化
//同时清除缓存,避免大量数据造成内存溢出
if(i%20==0){
session.flush();
session.clear();
}
}
session.getTransaction().commit();
}catch(Exceptione){
e.printStackTrace();
session.getTransaction().rollback();
}finally{
HibernateUtils.closeSession(session);
}
}
}
(二)二级缓存(开启两个Session可以共享缓存数据,如果不设置查询缓存只能缓存单实体对象,设置后可缓存集合对象)
ehcache.xml
xmlversion="1.0"?
>
--Setsthepathtothedirectorywherecache.datafilesarecreated.
IfthepathisaJavaSystemPropertyitisreplacedby
itsvalueintherunningVM.
Thefollowingpropertiesaretranslated:
user.home-User'shomedirectory
user.dir-User'scurrentworkingdirectory
java.io.tmpdir-Defaulttempfilepath-->
--内存不足开启磁盘缓存Java.io.tmpdir目录在运行时会根据相对路径生成。
-->
maxElementsInMemory="10000"
eternal="false"
timeToIdleSeconds="120"
timeToLiveSeconds="120"
overflowToDisk="true"
/>
--Predefinedcaches.Addyourcacheconfigurationsettingshere.
IfyoudonothaveaconfigurationforyourcacheaWARNINGwillbeissuedwhenthe
CacheManagerstarts
ThefollowingattributesarerequiredfordefaultCache:
name-Setsthenameofthecache.Thisisusedtoidentifythecache.Itmustbeunique.
maxInMemory-Setsthemaximumnumberofobjectsthatwillbecreatedinmemory
(缓存中最大允许创建的对象数)
eternal-Setswhetherelementsareeternal.Ifeternal,timeoutsareignoredandtheelement
isneverexpired.
(缓存中对象是否为常量,如果是,超时设置将被忽略,对象从不过期)
timeToIdleSeconds-Setsthetimetoidleforanelementbeforeitexpires.Isonlyused
iftheelementisnoteternal.Idletimeisnow-lastaccessedtime
(缓存数据钝化时间(设置对象在它过期之前的空闲时间))
timeToLiveSeconds-Setsthetimetoliveforanelementbeforeitexpires.Isonlyused
iftheelementisnoteternal.TTLisnow-creationtime
(缓存数据的生存时间(设置对象在它过期之前的生存时间))
overflowToDisk-Setswhetherelementscanoverflowtodiskwhenthein-memorycache
hasreachedthemaxInMemorylimit.
(内存不足时,是否启用磁盘缓存)
-->
--
1、timeToLiveSeconds的定义是:
以创建时间为基准开始计算的超时时长;
2、timeToIdleSeconds的定义是:
在创建时间和最近访问时间中取出离现在最近的时间作为基准计算的超时时长;
3、如果仅设置了timeToLiveSeconds,则该对象的超时时间=创建时间+timeToLiveSeconds,假设为A;
4、如果没设置timeToLiveSeconds,则该对象的超时时间=min(创建时间,最近访问时间)+timeToIdleSeconds,假设为B;
5、如果两者都设置了,则取出A、B最少的值,即min(A,B),表示只要有一个超时成立即算超时
-->
maxElementsInMemory="10000"
eternal="false"
timeToIdleSeconds="300"
timeToLiveSeconds="600"
overflowToDisk="true"
/>
--SamplecachenamedsampleCache2
Thiscachecontains1000elements.Elementswillalwaysbeheldinmemory.
Theyarenotexpired.-->
maxElementsInMemory="1000"
eternal="true"
timeToIdleSeconds="0"
timeToLiveSeconds="0"
overflowToDisk="false"
/>-->
hibernate.cfg.xml
jdbc:
mysql:
//localhost/hibernate_cache
com.mysql.jdbc.Driver
root
root
org.hibernate.dialect.MySQLDialect
true
--开启二级缓存-->
true
--指定缓存产品提供商-->
org.hibernate.cache.EhCacheProvider
--指定二级缓存的类,不指定二级缓存就不会缓存-->
publicclassCacheLevel2TestextendsTestCase{
/**
*开启两个session,分别调用load
*/
publicvoidtestCache1(){
Sessionsession=null;
try{
session=HibernateUtils.getSession();
session.beginTransaction();
Studentstudent=(Student)session.load(Student.class,1);
System.out.println("student.name="+student.getName());
session.getTransaction().commit();
}catch(Exceptione){
e.printStackTrace();
session.getTransaction().rollback();
}fin