.NET进阶 — Nhibernate 持久化的三种状态

引入

  在面向对象的开发中,程序的运行都是通过对象的方式对数据库进行增删改查的操作,必然在持久化过程中产生一些列的对象,比如登陆,必然会有实例化的UserEntity对象,从数据库Select出来的对象,Save到数据库的对象,如何区分这些对象以及当前会话的状态,下面看NHibernate中的对象状态的管理:


Nhibernate 三态


Nhibernate在持久化对象的生命周期,将对象分为三个状态:

1、瞬时态(Transient

  也叫临时态,顾名思义,对象是临时创建的,即刚实例化的对象:

  UserEntityenUser = new UserEntity();

  这个enUser对象现在就处于瞬时态,因为此时只是给enUser对象分配了一块内存空间,还没有进入NhibernateSession缓存,更没有持久化到数据库。

  瞬时对象特点:

  对象在数据库没有记录,也不和Session关联。

 

2、持久态(Persistent

  瞬时对象被保存到数据库或者从数据库查询来的对象,并且还在Session管理中的对象。

  瞬时对象转化为持久对象:(1)通过SessionSave()SaveOrUpdate()方法将瞬时对象持久化到数据库,(2)通过Get()Load()等查询方法查询到数据对象。

  持久化对象的特点:

  对象与数据库中记录同步,并且数据变更处于Session的管理之下。

 

3、游离态(Detached

  由持久态转换而来,在与持久化对象关联的Session被关闭后,对象就变成游离态,但是还拥有持久化对象的所有属性。

  游离对象的特点:

  和瞬时对象一样,都没有处于Session关联。不同的是游离对象是经过持久化的对象,在数据库中有记录。

 

三态间的转换

  以上简单的介绍了Nhibernate持久化的三个状态,在持久化对象的生命周期内,这三个状态并不是孤立的,它们之间存在的相互转换的过程:

状态分析:

1、瞬时态转换成持久态

//瞬时态对象

UserEntity enUser = new UserEntity();

enUser.name = "yiming";

//关联Session,调用Save(enUser)持久化到数据库,状态变为持久态,但是还没有更新到数据库,需要在进行flush()

Session.Save(enUser);

enUser.name = "liuming";

Session.Save(enUser); //无效

//session的缓存中的数据与数据库同步,关闭Session

Session.Flush();

说明:当执行持久化操作时,持久化操作并没有立即执行(更新到数据库),而是被记录下来,直到Session.Flush时才会实际更新到数据库,这样做的原因很容易理解,就是为了避免频烦的数据库连接操作。如果没有调用Flush而关闭了会话,当前会话中的持久对象将不会持久化!并且对已经持久化的对象调用Save()或者Update()是没有意义的。

 

2、持久态转换成游离态

持久态转换成游离态就是一个清理Session的过程,通常不会手动去调用evict(),close(),clear()这些图中列出的方法,而是由Nhibernate去管理,清理的时机:

1、commit() 方法被调用时。

2、查询时会主动commit清理缓存,保证查询结果能反映对象的最新状态。

3、调用session.flush()方法。

 

3、游离态转换为持久态

update()方法为例:

Session.Update(enUser);

如果enUser是持久化对象,那么不进行任何操作,即可以同步到数据库。如果enUser是游离对象,那么就必须先转为持久对象,然后再同步到数据库。所以Update的时候也会发出select语句。

 

其他的方法不再一一说明,其实只要明白了这三种状态以及转换过程,结合我们以前通过sql语句的实现(因为Nhibernate的这些方法最终还是通过sql语句去操作数据库的)的经验去考虑,就很容易理解。

 

总结

  一个月的开发,在投诉系统中遇到最多的问题就是调用底层SaveUpdateSaveOrUpdate方法,以及在级联操作的过程中的问题,由于对这三个状态的不了解,错误不断,完全是一个方法一个方法的尝试,也摸索到了一些规律,再加上这次的学习对Nhibernate的三态更清晰了。


  本文也一直在出现一个词Session,这个词都不陌生,但NhibernateSession是我们之前用到Session吗,在Nhibernate中的作用是什么,带着问题进入下一篇(NHibernate 缓存机制)



郑重声明:本站内容如果来自互联网及其他传播媒体,其版权均属原媒体及文章作者所有。转载目的在于传递更多信息及用于网络分享,并不代表本站赞同其观点和对其真实性负责,也不构成任何其他建议。