Hibernate4从入门到精通三——————hibernate的三种状态


一、hibernate的三种状态讲解

transient(瞬时)状态表示刚刚new出来一个对象,但还没有在数据库中保存。

不处于Session的缓存中。
persistent(持久化)状态表示在数据库里面存在着该对象的一条记录。       
    当调用session.save()时就变成持久化状态。
detached(离线)状态表示数据库中有记录,但不在session的中。
关闭session时候




二、拷贝上个项目。

在org.zttc.itat.test包下新建Junit测试类

TestStatus.java

package org.zttc.itat.test;

import java.text.SimpleDateFormat;
import org.hibernate.Session;
import org.junit.Test;
import org.zttc.itat.model.User;
import org.zttc.itat.util.HibernateUtil;

public class TestStatus {
	private static final SimpleDateFormat sdf=new SimpleDateFormat("yyyy-MM-dd");
	
	@Test
	public void testTransient() {
		Session session=null;
		try {
			session=HibernateUtil.openSession();
			session.beginTransaction();
			User u=new User();
			u.setNickname("张小三");
			u.setPassword("123");
			u.setUsername("zhangsan");
			u.setBorn(sdf.parse("1999-11-11"));
			//以上u就是Transient状态,表示没有被session管理而且数据库中没有。
			//当执行了save之后,u被session所管理,而且数据库中会存在,就为persistent状态。
			session.save(u);
			
			session.getTransaction().commit();
		} catch (Exception e) {
			e.printStackTrace();
			if(session!=null) session.getTransaction().rollback();
		} finally{
			HibernateUtil.close(session);
		}
	}
	
	
	@Test
	public void testPersistent01() {
		Session session=null;
		try {
			session=HibernateUtil.openSession();
			session.beginTransaction();
			User u=new User();
			u.setNickname("赵小三");
			u.setPassword("828");
			u.setUsername("xiaozhao");
			u.setBorn(sdf.parse("1988-11-18"));
			//以上u就是Transient状态,表示没有被session管理而且数据库中没有。
			//当执行了save之后,u被session所管理,而且数据库中会存在,就为persistent状态。
			session.save(u);
			/*
			 * 此时u是持久化状态,已经被session所管理,当在提交时,即执行session.getTransaction().commit()语句,
			 * 会把session中的u和目前的u所比较。
			 * 如果两个u不一样,会继续发出相应的sql语句。
			 */
			u.setNickname("赵老三");
			/*
			 * 此时会发出两条sql语句:一条用来插入,一条用来更新。
			 * Hibernate: insert into t_user (username, password, nickname, born) values (?, ?, ?, ?)
			 * Hibernate: update t_user set username=?, password=?, nickname=?, born=? where id=?
			 */
			
			session.getTransaction().commit();
		} catch (Exception e) {
			e.printStackTrace();
			if(session!=null) session.getTransaction().rollback();
		} finally{
			HibernateUtil.close(session);
		}
	}
	
	@Test
	public void testPersistent02() {
		/*
		 * 会发出几条sql语句,执行结果是什么?
		 * 
		 */
		Session session=null;
		try {
			session=HibernateUtil.openSession();
			session.beginTransaction();
			User u=new User();
			u.setNickname("赵晓八");
			u.setPassword("009");
			u.setUsername("zxj");
			u.setBorn(sdf.parse("1976-1-5"));
			//执行save时候会发出insert语句。
			session.save(u); 
			
			u.setPassword("222");
			//这条save语句没用
			session.save(u);
			
			u.setNickname("赵三碰");
			//没有用
			session.update(u);
			
			u.setBorn(sdf.parse("1999-9-9"));
			//没有用,只有在commit并且对象不一样的时候才执行update语句
			session.update(u);
			
			session.getTransaction().commit();
			/*
			 * 会发出两条sql语句:
			 * Hibernate: insert into t_user (username, password, nickname, born) values (?, ?, ?, ?)
			 * Hibernate: update t_user set username=?, password=?, nickname=?, born=? where id=?
			 * 因为,执行save之后,处于持久化状态,session的所有操作都没用,
			 * 只有在session提交的时候会比较save之前的u和save之后的u是否改变,然后发出相应的sql语句。
			 */
		} catch (Exception e) {
			e.printStackTrace();
			if(session!=null) session.getTransaction().rollback();
		} finally{
			HibernateUtil.close(session);
		}
	}
	
	
	@Test
	public void testPersistent03() {		
		Session session=null;
		try {
			session=HibernateUtil.openSession();
			session.beginTransaction();
			User u=new User();
			u.setNickname("刘晓八");
			u.setPassword("009");
			u.setUsername("zxj");
			u.setBorn(sdf.parse("1976-1-5"));			
			session.save(u); 
			//一下三条语句没有用
			session.save(u);
			session.update(u);
			session.update(u);
			session.getTransaction().commit();
			/*
			 * 只会发一条sql语句,因为save前的u和save后commit之前的u一样。
			 */
		} catch (Exception e) {
			e.printStackTrace();
			if(session!=null) session.getTransaction().rollback();
		} finally{
			HibernateUtil.close(session);
		}
	}
	
	@Test
	public void testPersistent04() {		
		Session session=null;
		try {
			session=HibernateUtil.openSession();
			session.beginTransaction();
			//此时u是Persistent状态。因为u被session所管理了。
			User u=(User)session.load(User.class, 6);
			u.setUsername("aaa");
			session.getTransaction().commit();	
			/*
			 * 此时会发两条sql语句,一条select,一条update。因为session中的u对象变化了。
			 */
		} catch (Exception e) {
			e.printStackTrace();
			if(session!=null) session.getTransaction().rollback();
		} finally{
			HibernateUtil.close(session);
		}
	}
	
	@Test
	public void testPersistent05() {		
		Session session=null;
		try {
			session=HibernateUtil.openSession();
			session.beginTransaction();
			//此时u是Persistent状态。因为u被session所管理了。
			User u=(User)session.load(User.class, 6);
			session.getTransaction().commit();	
			u.setNickname("123");
			/*
			 * 此时发出1条sql语句select,因为commit已经执行完成了。
			 * 此时u还是Persistent状态。
			 */
		} catch (Exception e) {
			e.printStackTrace();
			if(session!=null) session.getTransaction().rollback();
		} finally{
			HibernateUtil.close(session);
		}
	}
	
	@Test
	public void testPersistent06() {		
		Session session=null;
		try {
			session=HibernateUtil.openSession();
			session.beginTransaction();
			//此时u是Persistent状态。因为u被session所管理了。
			User u=(User)session.load(User.class, 6);
			session.getTransaction().commit();	
			//commit结束后,下面的u任然是Persistent状态。
			u.setNickname("123");
			session.beginTransaction();
			session.getTransaction().commit();
			/*
			 * 会发两条sql语句
			 */
		} catch (Exception e) {
			e.printStackTrace();
			if(session!=null) session.getTransaction().rollback();
		} finally{
			HibernateUtil.close(session);
		}
	}
	
	@Test
	public void testDetached01() {		
		Session session=null;
		try {
			session=HibernateUtil.openSession();
			session.beginTransaction();
			User u =new User();
			u.setId(6);
			/*
			 * 此时u没有被session管理,是离线(detached)状态。注意和瞬时状态比较。
			 */
			u.setNickname("juke");
			//当执行save的时候总会添加一条数据。此时id会根据Hibernate所定义的规则生成。
			//因为id为6的已经存在,所以会开辟一个新的id为7的数据。
			session.save(u);
			session.getTransaction().commit();	
		} catch (Exception e) {
			e.printStackTrace();
			if(session!=null) session.getTransaction().rollback();
		} finally{
			HibernateUtil.close(session);
		}
	}
	
	@Test
	public void testDetached02() {		
		Session session=null;
		try {
			session=HibernateUtil.openSession();
			session.beginTransaction();
			User u =new User();
			u.setId(6);
			session.update(u);
			session.getTransaction().commit();	
			//这时候u会变成持久化状态,数据库中id为6的记录全变为空,因为其它值为空,即
			//username、nickname等等为空。
		} catch (Exception e) {
			e.printStackTrace();
			if(session!=null) session.getTransaction().rollback();
		} finally{
			HibernateUtil.close(session);
		}
	}
	
	@Test
	public void testDetached022() {		
		Session session=null;
		try {
			session=HibernateUtil.openSession();
			session.beginTransaction();
			User u =new User();
			u.setId(6);
			session.update(u);
			u.setBorn(sdf.parse("1921-1-1"));
			u.setNickname("bo");
			u.setPassword("hello");
			session.update(u);
			session.getTransaction().commit();	
			/*
			 * 此时会发出1条sql语句并把id为6的记录更新。
			 */
		} catch (Exception e) {
			e.printStackTrace();
			if(session!=null) session.getTransaction().rollback();
		} finally{
			HibernateUtil.close(session);
		}
	}
	
	@Test
	public void testDetached03() {		
		Session session=null;
		try {
			session=HibernateUtil.openSession();
			session.beginTransaction();
			User u =new User();
			u.setId(6);
			session.update(u);
			u.setBorn(sdf.parse("1921-1-1"));
			u.setNickname("bo");
			u.setPassword("hello");
			/*
			 * 把id更改了,会报错,如下。
			 * identifier of an instance of org.zttc.itat.model.User was altered from 6 to 90
			 *id为8的u是瞬时的,不存在于数据库中。虽然数据库中id为8有记录。但是下面这个
			 *id为8的u是新的,是瞬时的,和数据库中的不一样。
			 */
			u.setId(8);
			session.getTransaction().commit();	
		} catch (Exception e) {
			e.printStackTrace();
			if(session!=null) session.getTransaction().rollback();
		} finally{
			HibernateUtil.close(session);
		}
	}
	
	@Test
	public void testDetached04() {		
		Session session=null;
		try {
			session=HibernateUtil.openSession();
			session.beginTransaction();
			User u =new User();
			u.setId(6);
			session.delete(u);
			//执行完delete后u就是Transient对象。
			u.setNickname("bbb");//瞬时对象u不会被session管理,数据库中也不存在。所以这句话没用。			
			session.getTransaction().commit();	
		} catch (Exception e) {
			e.printStackTrace();
			if(session!=null) session.getTransaction().rollback();
		} finally{
			HibernateUtil.close(session);
		}
	}
	
	@Test
	public void testDetached05() {		
		Session session=null;
		try {
			session=HibernateUtil.openSession();
			session.beginTransaction();
			User u =new User();
			u.setNickname("juke");
			session.update(u);
			/*
			 * u是瞬时状态,瞬时状态在数据库中没有数据,执行update会报错。
			 */
			session.getTransaction().commit();	
		} catch (Exception e) {
			e.printStackTrace();
			if(session!=null) session.getTransaction().rollback();
		} finally{
			HibernateUtil.close(session);
		}
	}
	
	@Test
	public void testDetached051() {		
		Session session=null;
		try {
			session=HibernateUtil.openSession();
			session.beginTransaction();
			User u =new User();
			u.setId(7);
			u.setNickname("juke");
			session.saveOrUpdate(u);
			/*
			 * saveOrUpdate意思是:u是离线状态,会执行update。u是瞬时状态会执行save。
			 * 因为有setId,所以是离线状态,会执行update。
			 */
			session.getTransaction().commit();	
		} catch (Exception e) {
			e.printStackTrace();
			if(session!=null) session.getTransaction().rollback();
		} finally{
			HibernateUtil.close(session);
		}
	}
	
	
	@Test
	public void testDetached06() {		
		Session session=null;
		try {
			session=HibernateUtil.openSession();
			session.beginTransaction();
			//u1是Persistent状态
			User u1 =(User) session.load(User.class, 7);
			System.out.println(u1.getUsername());
			//u2没有被session管理,而且在数据库中存在这样的id,所以是detached状态。
			User u2=new User();
			u2.setId(7);
			u2.setPassword("2225555");
			/*
			 * 当执行下面语句时候u2变成Persistent状态,这时候在session中就会存在两份相同的对象,会报错。
			 * 但是把下面这句话换成session.merge(u2)就行了,因为merge会判断
			 * session中是否存在两份相同的对象如果存在,会把它们合并。
			 * 但是merge方法一般不用。
			 */
			session.saveOrUpdate(u2);         //session.merge(u2);
			
			session.getTransaction().commit();	
		} catch (Exception e) {
			e.printStackTrace();
			if(session!=null) session.getTransaction().rollback();
		} finally{
			HibernateUtil.close(session);
		}
	}	
	
	@Test
	public void testClear() {		
		Session session=null;
		try {
			session=HibernateUtil.openSession();
			session.beginTransaction();
			User u =(User) session.load(User.class, 7);
			u.setNickname("zhan");
			//清空session后,Persistent对象不存在。不会发update语句,数据库也不会变化。
			session.clear();
			session.getTransaction().commit();	
		} catch (Exception e) {
			e.printStackTrace();
			if(session!=null) session.getTransaction().rollback();
		} finally{
			HibernateUtil.close(session);
		}
	}	
}



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值