`
天上掉下个喜欢编程的榕哥哥
  • 浏览: 28261 次
  • 性别: Icon_minigender_1
  • 来自: 广州
社区版块
存档分类
最新评论

Hibernate的Session对数据库操作的实际过程

    博客分类:
  • Java
阅读更多

         之前只是简单的了解像flush、commit、evict这些方法,而且对实际的执行过程也缺乏了解,在做一些项目的时候也因此导致出现一些错误。通过查阅一些资料后才知道原来是怎么一回事,以下是自己整理的一点东西,给有需要的人看看。

 

        之前使用hibernate框架的时候经常会忘记了在我们的应用程序与数据库之间还隔了一Hibernate,只是简单的认为通过session对数据库操作就是高一层JDBC的封装而已,但Hibernate在为我们提供持久化服务的同时,其实它改变了我们对数据库的操作方式,这种方式使我们不再像是JDBC一样直接对数据库操作,而是有着很多的不同,如果没有正视这一点,在应用Hibernate的时候往往会出现一些不好的结果。

 

有什么不同?

      最大的不同就是Hibernate在我们的应用程序与数据库之间增加了一个缓存区。每Session是通过一些映射和集合来维护所有与该Session建立了关联的对象实体以及对这些对象实体所进行的操作

     主要映射与集合:

            entityEntries:保存与Session建立了关联的对象实体的映射,包含了对象实体的状态信

                                     息。

            insertions:所有的插入操作集合,在一次事务中所有的插入操作都会被记录进来。

             deletions:所有删除操作集合,在一次事务中所有删除操作都会被记录进来。

               updates:所有更新操作集合,在一次事务中所有更新操作都会被记录进来。

      我们平时使用session中的方法对数据库进行操作的时候,实际的执行过程与上面的的缓存的映射、集合有很大关系。

 

刚学Hibernate的时候我错误的认为:

         session.save(obj);

        错误认为上面这句代码执行的时候就会将对象实体进行缓存并保存到数据库,但Hibernate并未将这个对象实际的写入数据库中,而仅仅是将obj这个对象放入entityEntries(因为此时obj已经与缓存建立了关联了),由于现在是要对obj对象进行插入操作,Session还要在insertions中登记这个插入行为,在真正需要将缓存中的数据flush(事务提交的时候会调用此方法)入数据库时才执行先前登记的所有行为(有多个数据库操作,会分别一起先登记到对应的操作集合)。

 

理解了上面说实际执行过程之后,看一个简单的例子:

   

   Session s = HibernateSessionFactory.openSession();
   Obj obj = new Obj();
   Transaction tx = s.beginTransaction(); 
   s.save(obj); 
   s.evict(obj); 
   tx.commit(); 
   s.close();

    如果觉得上面的代码没有错误那么说明也没能理解好hibernate对数据库操作的实际过程。

    以上代码中的s.evict(obj)将obj对象实体从session缓存中清除,会从entityEntries中将obj这个  

    对象移出。

    事务提交时,需要将所有缓存中的对象实体flush入数据库,这个时候obj不在entityEntries中是没有什么关系的,因为在执行insert的行为时只需要访问insertions集合就足够了,所以此时不会有任何的异常。但执行完插入后异常就出现了,在插入完成后需要entityEntries中obj的标记为已存在数据库中,但obj已经不存在于entityEntries中,此时就会出现异常。

 

学习中还有一个比较容易模糊的是:flush

        session中的flush主要做两件事:

       1、清理缓存

       2、强制数据库与缓存中的对象实体进行同步,保证数据的一致性

要注意的是在进行flush的时候,是有顺序的:hibernate会将之前已经登记到insertions这些操作集合的所有行为按照insert、update、delete的顺序提交操作的,但它也并不会向数据库提交事务(未持久化到数据库,还可以rollback),也就是数据库中的数据还没有变动。

 

看个例子:

 

     

   Session s = HibernateSessionFactory.openSession();
   User user1 = new User();
   user1.setU_id("1");//这里u_id是主键
   s.save(user1); //保存对象
   user1.setU_id("2");//更改主键
   s.update(User1);//更新对象

   User user2 = new User();
   user2.setU_id("1");
   s.save(user2);
   s.flush();

   上面的代码会产生主键冲突,这就跟上面说的flush提交操作的顺序有关。

   虽然s.save(user2)写在了s.update(user1)后面,但flush提交操作的时候会按顺序先将登记在insertions集合里的操作行为都提交执行后再提交updates集合里的。所以在执行s.save(user1)之后就执行了s.save(user2),从而出现主键冲突。

 

        在使用hibernate的时候,单纯简单的了解的话有可能会带来一些不确定的情况,通过了解多一点的实际操作过程与内部机制,会帮助我们写出更好的代码,所以我还是强调:做一个较真的技术人。

 

2
4
分享到:
评论

相关推荐

    Hibernate中的query 分页.doc

    数据库分页实际上是利用数据库本身SQL扩展的功能进行分页,例如MySQL的 limit 0,50这样的SQL语句。不但速度快,而且非常节省内存。不过不是每种数据库的都有这种分页支持的SQL,例如SQL Server就不支持。 4.scroll...

    第24次课-1 Spring与Hibernate的整合

    HibernateTemplate还提供了一种更灵活的方式来操作数据库,通过这种方式可以完全使用Hibernate的操作方式。 HibernateTemplate的灵活访问方式是通过如下两个方法完成的: Object execute(HibernateCallback action) ...

    支持多数据库的ORM框架ef-orm.zip

    而本质上,当我们调用某H框架的session.get、session.load、session.delete时,我们是想传递一个以对象形式表达的数据库操作请求。只不过某H框架要求(并且限制)我们将其视作纯粹的“单个”对象而已。JPA 2.0为了...

    hibernate get load区别

    get方法首先查询session缓存,没有的话查询二级缓存,最后查询数据库;反而load方法创建时首先查询session缓存,没有就创建代理,实际使用数据时才查询二级缓存和数据库

    ssh(structs,spring,hibernate)框架中的上传下载

    所以要完成对Lob字段的操作,Hibernate必须执行两步数据库访问操作,先Insert再Update。  使用BlobByteArrayType字段类型后,为什么我们就可以象一般的字段类型一样操作Blob字段呢?可以确定的一点是:...

    基于J2EE框架的个人博客系统项目毕业设计论文(源码和论文)

    我们掌握了数据库及其应用技术、数据库原理、计算机网络技术等课程,对数据库的设计、应用、维护及局域网的组成有了深刻的认识与一定的动手实践能力,考取了信息处理、程序设计、数据库技术等国家IT认证。...

    Hibernate save() saveorupdate()的用法第1/2页

    一个PO有三种状态: 1、未被持久化的VO 此时就是一个内存对象VO,由JVM管理生命周期 2、已被持久化的PO,并且在Session生命周期内 此时映射数据库数据,由数据库管理生命周期 3、曾被持久化过,但现在和Session已经...

    Web开发+java+ssh框架

    Hibernate是一个开放源代码的对象关系映射框架,它对JDBC进行了非常轻量级的对象封装,使得Java程序员可以随心所欲的使用对象编程思维来操纵数据库。 Hibernate可以应用在任何使用JDBC的场合,既可以在Java的客户端...

    Spring面试题

    当Hibernate在查询数据的时候,数据并没有存在与内存中,当程序真正对数据的操作时,对象才存在与内存中,就实现了延迟加载,他节省了服务器的内存开销,从而提高了服务器的性能。 3.Hibernate中怎样实现类之间的...

    s2sh + extjs4 办公平台架构

    4、使用p6spy 打印出hibernate 中已经替换了占位符参数的sql语句,为hibernate的调试不在感到苦恼 系统部署我使用的ant 部署,代码包含ant部署文件 skyline\coding\src\config\jdbc.properties 为数据库配置...

    java面试题

    Hibernate持久化:Hibernate根据定义的映射规则将对象持久化保存到数据库,这就实现了对象的持久化。 Spring由那几个模块组成? 答:Spring主要由7个模块组成: 1:Spring核心容器:提供了Spring框架的基本功能 2...

    火炬博客系统7

    Hibernate用来作持久层部分和域模型层部分,负责存储、更新、删除、查询数据库记录等,用来作DAO处理,本系统使用Spring整合Hibernate,spring为Hibernate的session提供了有效的容易和安全的控制,Spring控制...

    火炬博客系统6

    Hibernate用来作持久层部分和域模型层部分,负责存储、更新、删除、查询数据库记录等,用来作DAO处理,本系统使用Spring整合Hibernate,spring为Hibernate的session提供了有效的容易和安全的控制,Spring控制...

    火炬博客系统5

    Hibernate用来作持久层部分和域模型层部分,负责存储、更新、删除、查询数据库记录等,用来作DAO处理,本系统使用Spring整合Hibernate,spring为Hibernate的session提供了有效的容易和安全的控制,Spring控制...

    ibatis 开发指南(pdf)

    恍惚之际,只好再摸出JDBC 准备拼死一搏……,说得未免有些凄凉,直接使用JDBC 进行数据库操作实际上也是不错的选择,只是拖沓的数据库访问代码,乏味的字段读取操作 令人厌烦。 “半自动化”的ibatis,却...

    springmybatis

    3. 在session 中完成对数据的增删改查和事务提交等. 4. 在用完之后关闭session 。 5. 在java 对象和 数据库之间有做mapping 的配置文件,也通常是xml 文件。 mybatis实战教程(mybatis in action)之一:开发环境搭建 ...

    Grails 技术精解与Web开发实践【源码+样章】----下载不扣分,回帖加1分,欢迎下载,童叟无欺

    6.3.2 使用Session维持会话 74 6.3.3 自定义Codec实现对 密码加密 75 6.4 登录保护 76 6.5 本章小结 79 第7章 购物车与订单 80 7.1 购物车的查看与管理 80 7.1.1 定义购物车的Domain类 80 7.1.2 定义OrderService类...

    Java面试宝典2010版

    10、在weblogic管理制台中对一个应用域(或者说是一个网站,Domain)进行jms及ejb或连接池等相关信息进行配置后,实际保存在什么文件中? 11、说说weblogic中一个Domain的缺省目录结构?比如要将一个简单的helloWorld.jsp...

    最新Java面试宝典pdf版

    9、hibernate中的update()和saveOrUpdate()的区别,session的load()和get()的区别。 122 10、简述 Hibernate 和 JDBC 的优缺点? 如何书写一个 one to many 配置文件. 122 11、iBatis与Hibernate有什么不同? 122 12、...

Global site tag (gtag.js) - Google Analytics