Hibernate之对象的三种状态

Hibernate之对象的三种状态

Hibernate是一个与数据库打交道的持久层框架,当我们在操作对象的时候,会有以下三种状态。

/*上面获取Hibernate连接的代码省略,下面进行对对象的操作*/
Customer c = new Customer();//此时该对象没有ID,没有与session关联,称之为“瞬时状态”
c.setName("张三");//此时还是瞬时状态,无ID,无session关联。
session.save(c);//此时对象为有ID,有session关联的“持久化状态”;这里的save()方法并不是为了存储对象,而是为了将对象从“瞬时状态”变成“持久化状态”,这个在下面解释中详细讲解;
//提交事务
tx.commit();
session.close();//当session关闭了之后,所有对象又失去了session关联,但是在存储时又有了ID,此时便是一个有ID,但是没有session关联的状态,该状态称之为“游离状态(托管状态)”

当创建对象,一直到使用session存储对象之前,对象的状态为瞬时状态;

当使用session来存储对象的时候,此时便使用策略生成了ID,也有了session关联,此时为“持久化状态”;

当session关闭之时,所有对象都失去关联,但是存在ID,此时为“游离(托管)状态”;

session.save(Object obj)方法作用

在我们使用session.save()时,对象从“瞬时状态”变成了“持久化状态”,这里的作用也是如此,是为了进行对象的状态转换,而不是存储对象;根据主键生成策略的不同,Hibernate转换对象状态的方式也不同。当生成策略为“native”的时候,Hibernate会进行Insert()插入数据操作,然后拿到对象的ID,从而进行状态转换;当生成策略为“Increment”->主键自增的时候,Hibernate会进行Select()查询操作来获取当前对象ID,从而进行的状态转换。


为什么Hibernate要将对象分为三种状态,为什么要将对象从“瞬时状态”变成“持久化状态”呢?“持久化状态”有什么作用?
下面进行一个一个的解答:

“为什么要分为三种状态”:三种状态,其本质大家可以想想,是不是这样的,当我们创建了对象还没有存储,数据库表中没有主键与本对象ID相等的记录,因为还没有ID,如果你设置了一个表记录里没有的ID,那也是没有相等的,同样还是“瞬时状态”;当我们执行了save方法,对象有了就记录主键对应的ID,并且对象的其他所有属性值也与表的字段值相等,此时就是“持久化状态”;当时如果此时我们修改一个属性,用当前对象使用setName(“李四”)方法更换一个属性值,这时虽然ID与表中一条记录主键相等,但是其他的属性不尽相同,这时状态就会变成“游离(托管)状态”。这时我们只需要调用一个方法就又可以将对象转换成“持久化状态”,对了,就是update方法,我们只要将表记录更新成与当前对象一样(主键与其他字段值都分别相等),这时又会变成“持久化状态”,当然,Hibernate也会自动帮我们做这个更新操作,会尽量让对象保持持久化状态;

“持久化状态”的作用:我们使用Hibernate框架时会发现,我们已经摆脱了对数据库的直接操作,正因为Hibernate的“ORM对象关系映射模型”的存在,我们操作数据库会简单很多,甚至已经模糊了数据库表的操作,当我们需要创建数据库表,直接创捷对应的实体类,Hibernate就会帮我们创建;当我们需要插入表数据,也是只需要创建对象,封装数据,然后调用save方法即可,无需写增的sql语句;当我们需要修改和查询的时候,也有对应的update和query方法与之对应,当需要进行条件筛选时,也是使用的实体类对象中的属性名,而不是真正数据库表中的字段名;这更加让我们对“操作数据库表就是在操作实体类对象”这一概念在我们脑海中更深了。然而这一切都需要建立在对象是“持久化状态”的基础上,当对象是“持久化状态”,ORM关系映射才会发挥作用,那时我们对对象的操作就是对实际数据库表中记录的操作。比如我们拿到一个对象,使用set()方法修改其中的一个属性值的时候,Hibernate就会自动对数据库表中的记录属性对应的字段值进行修改。

“为什么要将对象从瞬时状态转换成持久化状态,一直保持在持久化状态”:
上面也带到了这一点,当对象处于持久化状态时,我们所操作的对象就会与数据库表形成映射,所有对对象的操作都会反应到数据库表上

猜你喜欢

转载自blog.csdn.net/qq_37766993/article/details/82712603