设为首页 加入收藏

TOP

Hibernate 悲观锁与乐观锁
2017-03-30 14:17:51 】 浏览:5498
Tags:Hibernate 悲观 乐观

业务逻辑的实现过程中,往往需要保证数据访问的排他性。因此,我们就需要通过一些机制来保证这些数据在某个操作过程中不会被外界修改,这样的机制,在这里,也就是所谓的“锁”,即给我们选定的目标数据上锁,使其无法被其它程序修改。


Hibernate 支持两种锁机制:


从加载对象就开始锁定。修改过程中一直是锁。直到事务commit()提交后再解锁。


session.load(Info.class,"p003",LockOptions.UPGRADE);


并不是真的锁,是在提交时间进行冲突检测。把里面的内容与刚开始读取的内容对照一下,有问题就抛异常。相对于悲观锁而言,乐观锁机制采取了更加宽松的加锁机制。 


悲观锁大多数情况下依靠数据库的锁机制实现,以保证操作最大程度的独占性。但随之而来的就是数据库性能的大量开销,特别是对长事务而言,这样的开销往往无法承受。乐观锁机制在一定程度上解决了这个问题。乐观锁,大多是基于数据版本(Version)记录机制实现。何谓数据版本?即为数据增加一个版本标识,在基于数据库表的版本解决方案中,一般是通过为数据库表增加一个"version"字段来实现。 



 


乐观锁的工作原理 :


读取出数据时,将此版本号一同读出,之后更新时,对此版本号加一。此时,将提交数据的版本数据与数据库表对应记录的当前版本信息进行比对,如果提交的数据版本号大于数据库表当前版本号,则予以更新,否则认为是过期数据。 


配置:


1.在数据库表中加一个字段version



如果是数据库后加的version字段,那么实体类中必须要加上version并生成get、set方法


2.在映谢文件中配置<version name="version"> 这里注意version的位置,一定是要放置在id的后面 


配置完成后代码不用改变


由乐观锁引发的问题 


当两个不同的事务同时读取到一条数据并进行修改时,这个时候程序就会抛出org.hibernate.StaleObjectStateException: Row was updated or deleted by another transaction (or unsaved-value mapping was incorrect)异常。 

这里同样有两种情况 

一种是两个不同的事务的情况 


事务2提交时发现version的值不一样,这个时候就会抛出org.hibernate.StaleObjectStateException: Row was updated or deleted by another transaction (or unsaved-value mapping was incorrect)异常.


第二种情况是子事务的情况 


解决办法


1、捕获StaleObjectStateException异常,提示数据过时已被修改,让用户重新提交


2、尽量从业务方面去减小事务块,事务块越大,由乐观锁引起的问题的概率就越大


】【打印繁体】【投稿】【收藏】 【推荐】【举报】【评论】 【关闭】 【返回顶部
上一篇iMX6平台SylixOS I2C总线驱动开发 下一篇Jfinal中的validator理解详解

最新文章

热门文章

Hot 文章

Python

C 语言

C++基础

大数据基础

linux编程基础

C/C++面试题目