Hibernate学习笔记Session.evict(user)方法
@[TOC]Hibernate学习笔记Session.evict(user)方法
Hibernate学习笔记Session.evict(user)方法
首先我们要明白Session.flush(user)方法,这个方法主要做了三件事:
- 根据session缓存中的临时集合insertion中的state区中的数据(user对象),发送sql语句。
- 清空临时集合中的数据。
- 向session中的缓存map中的existsInDatebase状态设置为为true,表示数据库中已经有了这个数据。
接着来看session.evict(user);这句话表示将user对象从Session缓存中逐出,即从Session中的EntityEntries属性中逐出。这句话的作用就是清理session缓存,以防数据量过多,造成缓存的崩溃。
接着来看下面代码:
第一个例子:/*** 测试uuid主键生成策略*/public void testSave1() {Session session = null;Transaction tx = null;try {session = HibernateUtils.getSession();//通过session工厂获取session对象tx = session.beginTransaction();//开启事务User1 user = new User1();user.setName("李四");user.setPassword("123");user.setCreateTime(new Date());user.setExpireTime(new Date());session.save(user);//这里设置user的主键为userId,主键生成策略为uuid,所以调用完成save后,只是将user纳入到了session的管理,//不会发出insert语句,但是id已经生成,session(缓存)中existsInDatebase状态为false(数据库中并不存在)session.flush();//调用flush,hibernate会清理缓存,1,根据临时集合执行sql//如果数据库的隔离级别设置为为提交读,那么我们可以看到flush过的数据//2,清空临时集合中的数据//3,并且session中existsInDatebase状态为true(表示数据库中已经存在)//提交事务//默认情况下commit操作会先执行flush清理缓存,所以不用显示的调用flush//commit后数据是无法回滚的tx.commit();}catch(Exception e) {e.printStackTrace();tx.rollback();}finally {HibernateUtils.closeSession(session);}}
在native主键生成策略中,由于主键生成策略是uuid,所以在save的时候并不会发送sql语句进行保存,所以这个时候,如果使用session.evict(user);清理缓存中的user对象,那么无法成功commit,因为hiberbate清理完临时集合之后,需要将existsInDatebase状态为true,这个时候由于evict已经将user对象从session缓存中逐出,所以hibernate找不到相关数据,所以提交失败。
/*** 测试uuid主键生成策略中的session.evict(user)。*/public void testSave3() {Session session = null;Transaction tx = null;try {session = HibernateUtils.getSession();tx = session.beginTransaction();User1 user = new User1();user.setName("王五");user.setPassword("123");user.setCreateTime(new Date());user.setExpireTime(new Date());//因为user的主键生成策略采用的是uuid,所以调用完成save后,只是将user纳入到了session的管理//不会发出insert语句,但是id已经生成,session中existsInDatebase状态为falsesession.save(user);//将user对象从session(缓存)中逐出,即session的EntityEntries属性中逐出session.evict(user);//目的是清除map中的缓存中的user对象。//无法成功提交,因为hibernate在清理缓存时,在session的临时insertions集合中取出user对象进行insert操作后//需要更新entityEntries属性中的existsInDatabase为true,而我们采用evict已经将user从session的entityEntries//中逐出了,所以找不到相关数据,无法更新,抛出异常 tx.commit();}catch(Exception e) {e.printStackTrace();tx.rollback();}finally {HibernateUtils.closeSession(session);}}
解决方法:在session.exict(user);语句之前使用session.flush();,这样子hibernate会清理缓存,会将user对象保存到数据库中,将session中的insertions中的user对象清除,并且设置session中existsInDatebase的状态为true,那么在commit的时候,会根据session缓存中insertion中的state中的数据发送sql语句,由于之前已经将user对象从缓存中逐出,所以这个时候找不到user对象,于是就不会发送sql语句也不会更新existsInDatebase的状态,也不会出异常了。
看代码:
/*** 测试uuid主键生成策略*/public void testSave4() {Session session = null;Transaction tx = null;try {session = HibernateUtils.getSession();tx = session.beginTransaction();User1 user = new User1();user.setName("王五");user.setPassword("123");user.setCreateTime(new Date());user.setExpireTime(new Date());//因为user的主键生成策略采用的是uuid,所以调用完成save后,只是将user纳入到了session的管理//不会发出insert语句,但是id已经生成,session中existsInDatebase状态为falsesession.save(user);//flush后hibernate会清理缓存,会将user对象保存到数据库中,将session中的insertions中的user对象//清除,并且设置session中existsInDatebase的状态为truesession.flush();//将user对象从session中逐出,即session的EntityEntries属性中逐出session.evict(user);//可以成功提交,因为hibernate在清理缓存时,在session的insertions集合中无法找到user对象//所以就不会发出insert语句,也不会更新session中的existsInDatabase的状态tx.commit();}catch(Exception e) {e.printStackTrace();tx.rollback();}finally {HibernateUtils.closeSession(session);}}
使用native主键生成策略,毫无疑问,不用在session.evict之前显示调用flush方法,也是行的通的。因为他在save的时候就已经发送了sql语句了,然后commit的时候,找不到user对象之后,不会发送sql也是无所谓的了,因为之前已经发送过了。
看代码:
/*** 测试native主键生成策略*/public void testSave5() {Session session = null;Transaction tx = null;try {session = HibernateUtils.getSession();tx = session.beginTransaction();User2 user = new User2();user.setName("张三11");user.setPassword("123");user.setCreateTime(new Date());user.setExpireTime(new Date());//因为user的主键生成策略为native,所以调用session.save后,将执行insert语句,返回有数据库生成的id//纳入了session的管理,修改了session中existsInDatebase状态为true//如果数据库的隔离级别设置为非提交读,那么我们可以看到save过的数据session.save(user);//将user对象从session中逐出,即session的EntityEntries属性中逐出session.evict(user);//可以成功提交,因为hibernate在清理缓存时,在session的insertions集合中无法找到user对象//所以就不会发出insert语句,也不会更新session中的existsInDatabase的状态tx.commit();}catch(Exception e) {e.printStackTrace();tx.rollback();}finally {HibernateUtils.closeSession(session);}}
主键生成策略为designed的时候,分析思略和之前的一样,
看代码:
/*** 测试assigned主键生成策略* */public void testSave7() {Session session = null;Transaction tx = null;try {session = HibernateUtils.getSession();tx = session.beginTransaction();User3 user = new User3();user.setId("003");user.setName("张三");session.save(user);user.setName("王五");session.update(user);session.flush();User3 user3 = new User3();user3.setId("004");user3.setName("李四");session.save(user3);//Hibernate: insert into t_user3 (name, password, create_time, expire_time, user_id) values (?, ?, ?, ?, ?)//Hibernate: update t_user3 set name=?, password=?, create_time=?, expire_time=? where user_id=?//Hibernate: insert into t_user3 (name, password, create_time, expire_time, user_id) values (?, ?, ?, ?, ?)//因为我们在session.udpate(user)后执行了flush,所以在清理缓存时执行flush前的sql不会生成//sql会按照我们的意愿执行tx.commit();}catch(Exception e) {e.printStackTrace();tx.rollback();}finally {HibernateUtils.closeSession(session);}}
我们的对手不是天才,而是脚踏实地的人。
Hibernate学习笔记Session.evict(user)方法相关推荐
- hibernate学习笔记(总结)
hibernate学习笔记 课程内容 6 1 HelloWorld 6 2 Hibernate原理模拟-什么是O/R Mapping以及为什么要有O/R Mapping 6 3 常见的0/R框架(了解 ...
- 马士兵Hibernate学习笔记
马士兵hibernate学习笔记 课程内容 6课程内容 1 HelloWorld 6 2 Hibernate原理模拟-什么是O/R Mapping以及为什么要有O/R Mapping 6 3 常见的0 ...
- hibernate学习笔记二
上一篇关于hibernate学习笔记一,主要是作为hibernate的入门知识.没有和spring发生任何关系,这一篇我将把spring集成进去,看spring如何管理hibernate,还有和未使用 ...
- 《Go语言圣经》学习笔记 第六章 方法
<Go语言圣经>学习笔记 第六章 方法 目录 方法声明 基于指针对象的方法 通过嵌入结构体来扩展类型 方法值和方法表达式 示例:Bit数组 封装 注:学习<Go语言圣经>笔记, ...
- Ui学习笔记---EasyUI的使用方法,EasyLoader组件使用
Ui学习笔记---EasyUI的使用方法,EasyLoader组件使用 技术qq交流群:CreDream:251572072 1.使用之前导入文件: 这里用jquery-easyui-1.2.6 ...
- js学习笔记2 -- js使用方法
js学习笔记2 -- js使用方法 方法一,使用外部js文件(推荐使用) 方法二,写在script标签中 方法三,写到标签的onclick属性中 方法四,使用超链接 方法一,使用外部js文件(推荐使用 ...
- wyy课堂cmos模拟设计课学习笔记-gm/Id设计方法介绍及曲线仿真
wyy课堂cmos模拟设计课学习笔记-gm/Id设计方法及曲线仿真 总思路 需要的图像曲线 软件操作 举例说明 总思路 这在b站上也有教学视频:https://www.bilibili.com/vid ...
- 凸优化学习笔记 15:梯度方法
前面的章节基本上讲完了凸优化相关的理论部分,在对偶原理以及 KKT 条件那里我们已经体会到了理论之美!接下来我们就要进入求解算法的部分,这也是需要浓墨重彩的一部分,毕竟我们学习凸优化就是为了解决实际当 ...
- Hibernate学习笔记二:Session
Session概述 Session是Hibernate提供的最主要的接口,它提供了基本的保存, 更新, 删除和加载 Java 对象的方法. Session 具有一个缓存, 位于缓存中的对象称为持久化对 ...
最新文章
- Python学习笔记:循环语句
- Numpy中求向量和矩阵的范数
- 我国最新十大黑科技发布,颠覆你的想象!
- 前端学习:Vue.js基本使用
- iOS蓝牙BLE4.0通信功能
- 基于jquery的tab切换
- CAD数据与ArcGIS数据的互转换
- js 判断支持webgl_「WebGL基础」:第一部分
- 【YOLO家族】【论文翻译】YOLO 9000 /YOLO V2
- UDP与TCP报文格式,字段意义
- 计算机实验室安全知识心得体会,实验室安全知识宣传
- 使用HEVC官方编码器HM
- panabit连接控制
- 关卡 动画 蓝图 运行_虚幻4 UE4 蓝图之关卡蓝图实现自动开关门
- Xcode6内置环境变量(Build Setting Macros)
- CSDN博客如何更换皮肤
- ubuntu企业微信解决无法查看、发送图片
- 夫妻贷款买房需要注意什么
- [算法]发散思维能力题目
- 零知识证明:Sigma协议
热门文章
- MWC2018 大会5G成大热门 中国芯大有可为
- 431金融带计算机,金融硕士考研:考研金融431能带计算器吗?
- jQuery(4)——jQuery hide、show方法的简单了解
- 鸿蒙应用开发 | 选项卡(TabList / Tab)的功能和用法
- 模型5.4——斯皮尔曼spearman相关系数
- php 中 实例化对象的 赋值及 指针引用
- 捷联惯导系统学习6.6(Sage-Husa自适应滤波 )
- 如何提高网页的效率(下篇)——Use YSlow to know why your web Slow
- MATLAB中积分命令【计算无穷限积分(广义积分)的函数】
- Linux arm系统支持U盘exfat和ntfs