1.Session概述[理解]
①代表Hibernate程序和数据库之间的一次会话。
②Session功能
[1]维护了Hibernate中的一级缓存。
[2]执行CRUD操作。
2.Session缓存[理解]
①一级缓存给我们带来的好处
[1]减少访问数据库的次数,提升程序的性能
[2]可以通过操作持久化类的对象来操作数据库,简化开发
②基本操作
[1]flush:推送。把缓存中数据的修改“推送”到数据库中。
- 修改持久化对象的属性并不会立即发送SQL语句,而是执行了flush操作才会发送。
- 发送了增删改的SQL语句也并不会立即生效,必须在提交了事务之后才能够真正落实到数据库中。
[2]refresh:刷新。把数据库中数据的修改提取到缓存中,以保证缓存中数据的正确。
[3]clear:清空缓存。
③Hibernate会在哪些情况下执行flush操作
[1]手动调用flush()方法
[2]提交事务之前
[3]在执行HQL查询之前:目的是保证HQL查询得到的数据是最新的
④事务隔离级别
[1]并发问题
- 脏读
- 不可重复读
- 幻读
[2]隔离级别
- 读未提交:读取其他事务没有提交的修改,不能解决任何并发问题
- 读已提交:读取其他事务已经提交的修改,可以解决脏读的问题
- 可重复读:要求当前事务执行时,其他事务不能对当前字段进行修改,可以解决脏读和不可重复读问题
- 串行化:要求当前事务执行时,其他事务不能对当前数据库表进行操作,可以解决全部并发问题,但效率很低
3.持久化对象的状态[理解]
①Session对象管理持久化对象时,持久化对象会表现为四种不同的状态。
②四种状态
[1]临时状态
(1)OID值是否为null:是
(2)是否在Session缓存中:不在
(3)在数据库中是否有对应的记录:没有
Book book = new Book(null,"xxx");//临时状态
session.save(book);
|
[2]持久化状态
(1)OID值是否为null:否
(2)是否在Session缓存中:在
(3)在数据库中是否有对应的记录:有
Book book = (Book)session.get(Book.class,1);//持久化状态
|
Book book = new Book(null,"xxx");//临时状态
session.save(book);//持久化状态
|
[3]游离状态
(1)OID值是否为null:否
(2)是否在Session缓存中:不在
(3)在数据库中是否有对应的记录:有
Book book = new Book(1,"xx");//游离状态
session.update(book);//持久化状态
|
[4]删除状态
(1)OID值是否为null:否,但无效
(2)是否在Session缓存中:不在
(3)在数据库中是否有对应的记录:没有
Book book = new Book(1,"xx");//游离状态
session.delete(book);//删除状态
|
4.Session的核心方法[掌握]
①掌握目标
[1]操作层面目标:会使用Session的核心方法进行基本的CRUD的操作。
- 将一个对象保存到数据库
- 将一个对象从数据库删除
- 通过修改对象的属性值修改数据库中对应的记录中的数据
- 通过一个游离对象更新数据库中对应的记录
- 从数据库中加载一个对象
[2]理论层面目标:通过核心方法执行后持久化对象状态的变化,体会Session对持久化对象的管理。
②持久化对象的OID的值是不能修改的,因为OID的值是缓存中对象的唯一标识。
③get()方法加载一个对象时会首先查询缓存中是否存在,如果有则直接返回不访问数据库;如果没有则访问数据库查询这个对象,并且保存到缓存中
④load()方法在刚执行的时候其实并没有去查询数据库,返回的对象其实只是一个代理对象,这个代理对象中仅OID属性有值,其他属性都没有值,如果用到其他的非OID的属性值时,才会发送SQL语句查询数据库进而填充没有值的属性。这种加载方式在 Hibernate中称为
延迟加载,也叫
懒加载。
⑤
懒加载初始化异常的产生:加载一个对象时,如果没有一开始就读取它的全部属性值,而仅仅返回了代理对象,并且重新开启了Session缓存,导致 Hibernate无法通过缓存机制重新加载代理对象就会抛出这个异常。
org.hibernate.
LazyInitializationException
: could not initialize
proxy
- no Session
|
⑥update()方法其实并不是立即发送SQL语句,而是计划发送一条SQL语句,是否真的发送还需要在执行flush()操作决定,缓存中的数据有变化才会发送,否则不发送。
⑦update()方法更新一个游离对象时,如果OID的值在数据库中不存在,则会抛出异常。
⑧update()方法更新一个游离对象时,会首先将这个对象放入Session缓存变成一个持久化对象,但如果此时Session缓存中已经有一个OID重复的对象,则操作会失败。