hibernate框架学习笔记5:缓存

缓存不止存在与程序中,电脑硬件乃至于生活中都存在缓存

目的:提高效率

比如IO流读写字节,如果没有缓存,读一字节写一字节,效率低下

hibernate中的一级缓存:提高操作数据库的效率

示例:

抽取的工具类

package utils;

import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.cfg.Configuration;

public class HibernateUtils {
    private static SessionFactory sf;

    static{
        //1 创建,调用空参构造
        Configuration conf = new Configuration().configure();
        //2 根据配置信息,创建 SessionFactory对象
         sf = conf.buildSessionFactory();
    }

    //获得session => 获得全新session
    public static Session openSession(){
                //3 获得session
                Session session = sf.openSession();

                return session;

    }
    //获得session => 获得与线程绑定的session
    public static Session getCurrentSession(){
        //3 获得session
        Session session = sf.getCurrentSession();

        return session;
    }
}

测试类:

示例1:

package cache;

import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
import org.hibernate.cfg.Configuration;
import org.junit.Test;

import domain.Customer;
import utils.HibernateUtils;

//测试一级缓存
public class Demo {

    @Test
    //证明一级缓存存在
    public void fun1(){
        //1 获得session
        Session session = HibernateUtils.openSession();
        //2 控制事务
        Transaction tx = session.beginTransaction();
        //3执行操作

        Customer c1 = session.get(Customer.class, 1l);
        Customer c2 = session.get(Customer.class, 1l);
        Customer c3 = session.get(Customer.class, 1l);
        Customer c4 = session.get(Customer.class, 1l);
        Customer c5 = session.get(Customer.class, 1l);

        System.out.println(c3==c5);//true
        //4提交事务.关闭资源
        tx.commit();
        session.close();// 游离|托管 状态, 有id , 没有关联

        //结果(保证数据库中存在主键为1的数据):
        //这里调用了五次方法,但是只打印一次SQL语句
    }
}

原理:程序第一次调用get方法,hibernate发送SQL语句查询数据库,查询结果以ResulySet对象返回,

hibernate再组装成Customer(实体类对象),存入session缓存对象,对象返回给程序

第二次调用get方法,会先从缓存中查看是否存在id=1的Customer对象,如果有,直接返回缓存中的对象

多次调用原理相同

明显地发现:这里的缓存技术很好地提升了效率

示例2:

    @Test
    //
    public void fun2(){
        //1 获得session
        Session session = HibernateUtils.openSession();
        //2 控制事务
        Transaction tx = session.beginTransaction();
        //3执行操作

        Customer c1 = session.get(Customer.class, 1l);

        c1.setCust_name("哈哈");//4提交事务.关闭资源
        tx.commit();
        session.close();// 游离|托管 状态, 有id , 没有关联

    }

引入了快照的概念

原理:

上边的原理其实有省略,数据库返回结果后,hibernate组装的时候,其实组装了两个对象,

一个放入缓存中,一个放入快照,返回给程序的是缓存对象,程序第一次修改了缓存对象,事务提交,

这时候hibernate比较缓存中的对象和快照,如果有变化,会同步到数据库中,没有变化,什么都不做

这里就提高了效率,不会多次去数据库查询,只需要比对缓存中的对象,减少不必要地SQL查询语句

示例3:

    @Test
    //持久化状态对象其实就是放入session缓存中的对象
    public void fun3(){
        //1 获得session
        Session session = HibernateUtils.openSession();
        //2 控制事务
        Transaction tx = session.beginTransaction();
        //3执行操作

        Customer c1 = new Customer();
        c1.setCust_id(1l);//托管|游离

        session.update(c1);//c1被放入session缓存了

        Customer c2 = session.get(Customer.class, 1l);

        //4提交事务.关闭资源
        tx.commit();
        session.close();// 游离|托管 状态, 有id , 没有关联

    }

这段代码运行中,打印SQL的UPDATE语句

原因:缓存中不存在快照,c1放入session缓存中对比快照时候必然不一致,而c2这一句调用get方法后,依照上边的原理,才会运行SQL的UPDATE语句

所以,这段代码中真正使hibernate发送SQL语句的是c2这一行

原文地址:https://www.cnblogs.com/xuyiqing/p/8449143.html

时间: 2024-09-30 06:45:51

hibernate框架学习笔记5:缓存的相关文章

j2ee开发之hibernate框架学习笔记

hibernate框架技术重点学习笔记 1.针对不同的数据库,有不同的数据库实现类,使其符号对应的数据库? mysqlDaoImpl oracleDaoImpl ... ... 2.对象和表记录的转换存在着转换问题->orm,对象和关系的一种映射 3.框架:解决一种问题的方案集合! 4..配置文件 Xxx.cfg.xml  主配置文件 xxx.hbm.xml映射文件: 映射基础 普通属性 主键 集合属性 关联关系:一对多  多对一 多对多  一对一 继承结构 5.其他特性:数据库连接池  懒加载

hibernate 框架学习笔记---网上摘抄的一个非常好的例子

编写Spring+Hibernate框架下的应用,总是离不了编写一个通用的泛型GenericHibernateDao.查阅了网上不少的GenericHibernateDao实现,归纳整理为如下实现,供后续编码参考. 首先定义接口泛型DAO接口 GenericDao package com.th.huz; import java.io.Serializable;import java.util.Collection;import java.util.Iterator;import java.uti

hibernate框架学习笔记1:搭建与测试

hibernate框架属于dao层,类似dbutils的作用,是一款ORM(对象关系映射)操作 使用hibernate框架好处是:操作数据库不需要写SQL语句,使用面向对象的方式完成 这里使用eclipse工具搭建: 官网下载:https://sourceforge.net/projects/hibernate/files/hibernate-orm/5.0.7.Final/ 下载.zip文件后解压: lib文件夹下的required文件夹内的jar包为必须包: 另外还需要MySQL的驱动包:

hibernate框架学习笔记2:配置文件详解

实体类: package domain; public class Customer { private Long cust_id; private String cust_name; private String cust_source; private String cust_industry; private String cust_level; private String cust_linkman; private String cust_phone; private String c

hibernate框架学习笔记10:HQL查询详解

HQL语句中不可以出现与表有关的内容,而是对象的属性 实体类(注意配置文件): package domain; import java.util.HashSet; import java.util.Set; //客户实体 public class Customer { private Long cust_id; private String cust_name; private String cust_source; private String cust_industry; private S

hibernate框架学习笔记11:Criteria查询详解

创建实体类对象: package domain; import java.util.HashSet; import java.util.Set; //客户实体 public class Customer { private Long cust_id; private String cust_name; private String cust_source; private String cust_industry; private String cust_level; private Strin

hibernate框架学习之一级缓存

l缓存是存储数据的临时空间,减少从数据库中查询数据的次数 lHibernate中提供有两种缓存机制 ?一级缓存(Hibernate自身携带) ?二级缓存(使用外部技术) lHibernate的一级缓存即Hibernate操作数据时所对应的临时数据存储区域,这个区域是绑定Session对象的,也就是说每开启一个Session对象,就会产生对应的一级缓存空间,当Session对象关闭时,该空间内的数据,也就是其中保存的PO对象,会转化为DO对象. lHibernate的一级缓存是Session级别的

hibernate框架学习笔记4:主键生成策略、对象状态

创建一个实体类: package domain; public class Customer { private Long cust_id; private String cust_name; private String cust_source; private String cust_industry; private String cust_level; private String cust_linkman; private String cust_phone; private Stri

hibernate框架学习笔记7:HQL查询、Criteria查询

HQL查询:hibernate独有的查询语言 适用于不复杂的多表查询 示例: 实体类: package domain; public class Customer { private Long cust_id; private String cust_name; private String cust_source; private String cust_industry; private String cust_level; private String cust_linkman; priv