zoukankan      html  css  js  c++  java
  • Hibernate -- 操作持久化对象

    知识点2: session概述

    Session 接口是 Hibernate 向应用程序提供的操纵对数据库的最主要的接口,它提供了基本的保存,更新, 删除和加载Java对象的方法.

    知识点3:理解session的缓存

    Session 接口的实现中包含一系列的 Java 集合, 这些Java集合构成了 Session缓存.只要Session 实例没有结束生命周期,存放在它缓存中的对象也不会结束生命周期
    sessionsave()方法持久化一个对象时,该对象被载入缓存,以后即使程序中不再引用该对象,只要缓存不清空,该对象仍然处于生命周期中。当试图load()对象时,会判断缓存中是否存在该对象,有则返回。没有在查询数据库

    知识点4:清理session的缓存

    Session 具有一个缓存,位于缓存中的对象称为持久化对象,它和数据库中的相关记录对应. Session能够在某些时间点,按照缓存中对象的变化来执行相关的 SQL语句, 来同步更新数据库,这一过程被称为清理缓存(flush)
    默认情况下 Session 在以下时间点清理缓存:
    当应用程序调用 Transaction commit()方法的时,该方法先清理缓存(session.flush()),然后在向数据库提交事务(tx.commit())
    当应用程序执行一些查询操作时,如果缓存中持久化对象的属性已经发生了变化,会先清理缓存,以保证查询结果能够反映持久化对象的最新状态
    显式调用 Sessionflush()方法.
    区别:

         flush:进行清理缓存(此时缓存中的数据并不丢失)的操作,让缓存和数据库同步执行一些列sql语句,但不提交事务,

         commit:先调用flush()方法,然后提交事务.则意味着提交事务意味着对数据库操作永久保存下来。

         reresh:刷新,session和数据库同步,执行查询,把数据库的最新信息显示出来,更新本地缓存的对象状态.

         clear:清空缓存,等价于list.removeAll();

    知识点5:在hibernate中java对象的状态

    Hibernate 把对象分为 4 种状态持久化状态临时状态游离状态删除状态.

    Session 的特定方法能使对象从一个状态转换到另一个状态

     

     

    知识点15: 操纵持久化对象-get()  load()

    都可以根据给定的 OID 从数据库中加载一个持久化对象
    区别:
    当数据库中不存在与 OID 对应的记录时, load()方法抛出 ObjectNotFoundException异常, get() 方法返回 null
    两者采用不同的延迟检索策略

    示例代码:

    javabean 及 配置文件参考上篇blog的 Customer.java Order.java Customer.hbm.xml hibernate.cfg.xml Order.hbm.xml

    知识点示例代码:

    AppFlushClearRefreshCommit.java

    package cn.itcast.state;
    
    import java.util.Iterator;
    import java.util.Set;
    
    import org.hibernate.FlushMode;
    import org.hibernate.Session;
    import org.hibernate.SessionFactory;
    import org.hibernate.Transaction;
    import org.hibernate.cfg.Configuration;
    import org.junit.Test;
    
    public class AppFlushClearRefreshCommit {
    	private static  SessionFactory sf=null;
    	
    	static{
    		   Configuration config=new Configuration();
    	       config.configure("cn/itcast/state/hibernate.cfg.xml");
    	       config.addClass(Customer.class);
    	       config.addClass(Order.class);
    	       sf=config.buildSessionFactory();
    	}
    		
    	    /*
    	     * 知识点4_1:清理session的缓存  测试flush方法的使用
    	     */
    		@Test
    		public  void testFlush(){
    			   Session session=sf.openSession();
    			   Transaction tx=session.beginTransaction();
    			   
    			   Customer c=new Customer();
    			   c.setName("曹操");
    			   
    			   session.save(c);
    			   
    			   /*
    			    * 清理缓存,刷新session的一级缓存中数据到数据库中,让缓存中的数据跟数据库同步 方向缓存--->数据库
    			    *         缓存中的数据不丢失
    			    */
    			   
    			   session.flush();  //会产生insert语句,此时已经在数据库中,但数据库还没有确认
    			 
    			   tx.commit();  //数据库确认插入的数据
    			   session.close();
    		}
    		
    		/*
    		 * 知识点4_2:清理session的缓存  测试flush和clear方法的使用
    		 */
    		@Test
    		public  void testFlushClear(){
    			   Session session=sf.openSession();
    			   Transaction tx=session.beginTransaction();
    			   
    			   //从数据库查询出的客户放置到session的一级缓存中
    			   Customer c4=(Customer)session.get(Customer.class, 4); //select
    			   
    			   //清理缓存,缓存中的数据不丢失
    			   session.flush();
    			   //从session的一级缓存中获取要查询的数据
    			   Customer c5=(Customer)session.get(Customer.class, 4);  //不会产生select语句
    			   
    			   //清空缓存,session的一级缓存中的数据丢失
    			   session.clear();
    			   
    			   //缓存中已经没有数据了,需要重新查询数据库
    			   Customer c6=(Customer)session.get(Customer.class, 4);  //会产生select语句
    			   
    			   tx.commit();  //数据库确认插入的数据
    			   session.close();
    		}
    		
    		/*
    		 * 知识点4_4:清理session缓存    测试refresh方法的使用
    		 */
    		@Test
    		public  void tesRefresh(){
    			   Session session=sf.openSession();
    			   Transaction tx=session.beginTransaction();
    			   
    			   Customer c4=(Customer)session.get(Customer.class, 4); //select
    			   c4.setName("马超");
    			   
    			   //刷新数据库中的数据和缓存中的同步,方法向从数据库----> 缓存,产生select语句
    			   session.refresh(c4);
    			   
    			   tx.commit();  //数据库确认插入的数据
    			   session.close();
    		}
    				
    	   /*
    	    * 知识点4_5:清理session的缓存(设置缓存的清理模式)
    	    */
    		@Test
    		public  void testCacheMode11(){
    			   Session session=sf.openSession();
    			   Transaction tx=session.beginTransaction();
    			   
    			   //设置缓存的模式是自动模式
    			   Customer c=new Customer();
    			   c.setName("秦琼");
    			   
    			   session.save(c);
    			   
    			   tx.commit();  //产生insert语句
    			   
    			   session.close();
    		}
    		
    		   /*
    		    * 知识点4_5:清理session的缓存(设置缓存的清理模式)
    		    */
    			@Test
    			public  void testCacheMode12(){
    				   Session session=sf.openSession();
    				   Transaction tx=session.beginTransaction();
    				   
    				   //设置缓存的模式是自动模式
    				   Customer c=new Customer();
    				   c.setName("秦琼");
    				   session.save(c);
    				   
    				   session.flush();//产生insert语句
    				   tx.commit();  
    				   
    				   session.close();
    			}
    			
    			
    		 /*
    		    * 知识点4_5:清理session的缓存(设置缓存的清理模式)
    		    */
    			@Test
    			public  void testCacheMode13(){
    				   Session session=sf.openSession();
    				   Transaction tx=session.beginTransaction();
    				   
    				   //设置缓存的模式是从不清理缓存
    				   session.setFlushMode(FlushMode.NEVER);
    				   
    				   Customer c=new Customer();
    				   c.setName("秦琼");
    				   session.save(c);
    				   
    				   //该方法不清理缓存,不会产生insert语句,此时数据不能插入到数据库中
    				   tx.commit();  
    				   
    				   session.close();
    			}
    			
    			
    			 /*
    			    * 知识点4_5:清理session的缓存(设置缓存的清理模式)
    			    */
    				@Test
    				public  void testCacheMode14(){
    					   Session session=sf.openSession();
    					   Transaction tx=session.beginTransaction();
    					   
    					   //设置缓存的模式是从不清理缓存
    					   session.setFlushMode(FlushMode.NEVER);
    					   
    					   Customer c=new Customer();
    					   c.setName("秦琼");
    					   session.save(c);
    					  
    					   //该方法清理缓存
    					   session.flush(); //产生insert语句
    					   
    					   //该方法不清理缓存
    					   tx.commit();  
    					   
    					   session.close();
    				}
    				
    				
    			   /*
    			    * 知识点4_5:清理session的缓存(设置缓存的清理模式)
    			    */
    				@Test
    				public  void testBatchData(){
    					   Session session=sf.openSession();
    					   Transaction tx=session.beginTransaction();
    					   
    					   //设置缓存的模式是从不清理缓存
    					   session.setFlushMode(FlushMode.NEVER);
    					   
    					   for(int i=0;i<100000;i++){
    						   Customer c=new Customer();
    						   c.setName("朱仝"+i);
    						   session.save(c);
    						   if(i%1000==0){
    							   //清理缓存,数据已经存在数据库,就是没有确认
    							   session.flush();
    							   //清空缓存
    							   session.clear();
    						   }
    					   }
    					   
    					   //清理缓存
    					   session.flush();
    					   
    					   //该方法不清理缓存
    					   tx.commit();  
    					   
    					   session.close();
    				}
    					
    }
    

    AppState.java

    package cn.itcast.state;
    
    import org.hibernate.Session;
    import org.hibernate.SessionFactory;
    import org.hibernate.Transaction;
    import org.hibernate.cfg.Configuration;
    import org.junit.Test;
    
    public class AppState {
    	private static SessionFactory sf = null;
    
    	static {
    		Configuration config = new Configuration();
    		config.configure("cn/itcast/state/hibernate.cfg.xml");
    		config.addClass(Customer.class);
    		config.addClass(Order.class);
    		sf = config.buildSessionFactory();
    	}
    
    	/*
    	 * 知识点5:临时对象(transient)  对象的状态
    	 */
    	@Test
    	public void teststate() {
    		Session session = sf.openSession();
    		Transaction tx = session.beginTransaction();
    		
    		//刚刚创建一个对象,此时就是临时对象,OID=null
    		Customer c = new Customer();
    		c.setName("曹操");
    		System.out.println("c.getId()  "+c.getId()); //null
    		
    		//此时customer对象变为持久对象(持久对象有OID,OID不为空)处于session的缓存中
    		session.save(c);
    		System.out.println("c.getId()  "+c.getId());  //存在值
    
    		tx.commit(); // 数据库确认插入的数据
    		session.close();  //此时没有一级缓存了
    		
    		//session关闭后,此时c引用的对象转化为游离对象  不再处于 Session 的缓存中
    		System.out.println(c.getId()+"   "+c.getName());
    		
    		//此时对象不再被引用,被jvm回收
    		c=null;
    		
    /****************************************************************************************************************/		
    		session = sf.openSession();
    	    tx = session.beginTransaction();
    	    
    	    //c1在session的一级缓存中存在 是持久对象 
    		Customer c1=(Customer)session.get(Customer.class, 5);
    	    
    		//删除c1对象
    		session.delete(c1);
    		//此时c1变为删除对象
    	    
    		tx.commit(); // 数据库确认插入的数据
    		session.close();  //此时没有一级缓存了
    		
    		//session关闭后,此时c1为游离对象
    		
    /****************************************************************************************************************/
    	}
    	
    	
    	
    	/*
    	 * 知识点5:临时对象(transient)  对象的状态
    	 *   * evict()方法:该方法能将持久对象转化为游离对象
    	 */
    	@Test
    	public void testEvict() {
    		Session session = sf.openSession();
    		Transaction tx = session.beginTransaction();
    	
    		//c1在session的一级缓存中存在 是持久对象 
    		Customer c1=(Customer)session.get(Customer.class, 5);  //产生select语句
    		
    		//直接从session的一级缓存中查询数据
    		Customer c2=(Customer)session.get(Customer.class, 5);   //不产生select语句
    	    
    		//将session一级缓存中的对象转化为游离对象,此时该对象在session的一级缓存中不存在
    	    session.evict(c1);
    	    
    	   
    	    //该方法能将游离对象再转化为持久对象,此时该对象有存在session的一级缓存中
    	    session.update(c1);
    	    
    	    //在缓存中不存在该对象,所以要查询数据库
    		Customer c3=(Customer)session.get(Customer.class, 5);  //不产生select语句
    		
    	    
    		tx.commit(); // 数据库确认插入的数据
    		session.close();  //此时没有一级缓存了		
    	}
    }
    

    AppMethod.java

    package cn.itcast.state;
    
    import org.hibernate.Session;
    import org.hibernate.SessionFactory;
    import org.hibernate.Transaction;
    import org.hibernate.cfg.Configuration;
    import org.junit.Test;
    
    public class AppMethod {
    	
    	private static SessionFactory sf = null;
    
    	static {
    		Configuration config = new Configuration();
    		config.configure("cn/itcast/state/hibernate.cfg.xml");
    		config.addClass(Customer.class);
    		config.addClass(Order.class);
    		sf = config.buildSessionFactory();
    	}
    
    	/*
    	 * 知识点12: 操纵持久化对象-save()
    	 */
    	@Test
    	public void testSave() {
    		Session session = sf.openSession();
    		Transaction tx = session.beginTransaction();
    	    
    		Customer c=new Customer();
    	    c.setId(3);  //没有用途
    		c.setName("西门庆");
    	    session.save(c);
    	    
    		tx.commit();
    		session.close();
    	}
    	
    	/*
    	 * 知识点13_1: 操纵持久化对象-update()
    	 */
    	@Test
    	public void updagePersission() {
    		Session session = sf.openSession();
    		Transaction tx = session.beginTransaction();
    	    
    		//持久对象
    		Customer c=(Customer)session.get(Customer.class, 7);
    		
    		//游离对象
    		session.evict(c);
    		
    		//游离对象---->持久对象  ---执行update语句
    		session.update(c);
    		
    		tx.commit();
    		session.close();
    	}
    	
        /*
    	 * 知识点13_2: 操纵持久化对象-update()
    	 *  * 在customer.hbm.xml文件的class标签中增加 select-before-update="true"(在执行更新之前查询)
    	 *      * 目的:把要更新的信息又防止到session的一级缓存中,快照有一份
    	 *      * 在更新时,哪缓存中的数据和快照比对,没有变化,不再产生update语句
    	 */
    	
    	@Test
    	public void updagePersissionClass() {
    		Session session = sf.openSession(); 
    		Transaction tx = session.beginTransaction();
    	    
    		//持久对象
    		Customer c=(Customer)session.get(Customer.class, 7);
    		
    		//游离对象
    		session.evict(c);
    		
    		//游离对象---->持久对象  ---执行update语句
    		session.update(c);
    		
    	    
    		tx.commit();
    		session.close();
    	}
    	
    	/*
    	 * 知识点13_3: 操纵持久化对象-update()
    	 */
    	@Test
    	public void updagePersissionOId() {
    		Session session = sf.openSession(); 
    		Transaction tx = session.beginTransaction();
    	    
    		//查询数据库  c1持久对象
    		Customer c1=(Customer)session.get(Customer.class, 7);
    		
    		//c1游离对象
    		session.evict(c1);
    		
    		//查询数据库  c2持久对象
    		Customer c2=(Customer)session.get(Customer.class, 7);
    		
    		//c1持久对象
    		session.update(c1);
    	    
    		tx.commit();
    		session.close();
    	}
    	
    	/*
    	 * 知识点13_4: 操纵持久化对象-update()
    	 */
    	@Test
    	public void updagePersissionWithNoData() {
    		Session session = sf.openSession(); 
    		Transaction tx = session.beginTransaction();
    	    
    		//查询数据库  c1持久对象
    		Customer c1=(Customer)session.get(Customer.class, 7);
    		
    		//c1游离对象
    		session.evict(c1);
            
    		System.out.println("cccccccccccccccc");
    		//手动删除数据
    		
    		//c1持久对象
    		session.update(c1);
    	    
    		tx.commit();
    		session.close();
    	}
    	
    	
    	/*
    	 * 知识点14_2: 操纵持久化对象-saveOrupdate()
    	 */
    	@Test
    	public void SaveOrUpdateTransient() {
    		Session session = sf.openSession();
    		Transaction tx = session.beginTransaction();
    	    
    		//临时对象
    		Customer c=new Customer();
    		c.setName("西门庆");
    
    		session.saveOrUpdate(c);
    	    
    		tx.commit();
    		session.close();
    	}
    	
    	
    	/*
    	 * 知识点14_3: 操纵持久化对象-saveOrupdate()
    	 *            如果是游离对象就用update方法
    	 */
    	@Test
    	public void updagePersissionDetached() {
    		Session session = sf.openSession(); 
    		Transaction tx = session.beginTransaction();
    	    
    		//查询数据库  c1持久对象
    		Customer c1=(Customer)session.get(Customer.class, 6);
    		
    		//c1游离对象
    		session.evict(c1);
           
    		//c1持久对象  执行update方法
    		session.saveOrUpdate(c1);
    	    
    		tx.commit();
    		session.close();
    	}
    	
    	/*
    	 * 知识点14_4: 操纵持久化对象-saveOrupdate()
    	 */
    	@Test
    	public void updagePersissionPersiss() {
    		Session session = sf.openSession(); 
    		Transaction tx = session.beginTransaction();
    	    
    		//查询数据库  c1持久对象
    		Customer c1=(Customer)session.get(Customer.class, 6);
    		
    		//c1持久对象  不会产生update语句
    		session.saveOrUpdate(c1);
    	    
    		tx.commit();
    		session.close();
    	}
    	
    	/*
    	 * 知识点14_5: 操纵持久化对象-saveOrupdate()
    	 *    saveOrUpdate(c)中判定对象为临时对象的标准
    	 *      * 如果Id为Integer类型(private Integer id)
    	 *         * 如果Id==null执行save操作
    	 *         * 如果Id!=null执行update操作
    	 *     *  如果javaBean中id为int类型(private int id;)此时id的默认值为0
    	 *        在Customer.hbm.xml文件 配置<id name="id" type="integer" unsaved-value="0">增加unsaved-value="0"
    	 *          * 如果javaBean中id属性的值与unsaved-value="0"相同,执行insert操作
    	 *          * 如果javaBean中id属性的值与unsaved-value="0"不相同,执行update操作
         
    	 */
    	@Test
    	public void SaveOrUpdateUnsaved() {
    		Session session = sf.openSession();
    		Transaction tx = session.beginTransaction();
    	    
    		//临时对象
    		Customer c=new Customer();
    	    
    		c.setName("西门庆");
    
    		session.saveOrUpdate(c);
    		System.out.println("c.getId()  "+c.getId());
    	    
    		tx.commit();
    		session.close();
    	}
    	
    	/*
    	 * 知识点15: 操纵持久化对象-get()  load()
    	 *   * 区别
    	 *      * 相同点:都是通过id查询对象
    	 *      * 不同点;
    	 *           * 如果id在数据库中不存在get返回null,load抛出异常
    	 *           * get方法总是立即加载,load可以配置延迟和立即两种(后面讲)
    	 * 
    	 */
    	@Test
    	public void getOrLoad() {
    		Session session = sf.openSession(); 
    		Transaction tx = session.beginTransaction();
    	    
    		Customer c1=(Customer)session.load(Customer.class, 14);
    	    System.out.println("c1  = "+c1);	
    	
    		tx.commit();
    		session.close();
    	}	
    }
    



     

  • 相关阅读:
    Linux下应急工具
    Windows NTLM Hash和Hash传递、Key传递攻击
    渗透中Meterpreter基本操作和对应的windows上的排查或者现象
    捕获一款无名挖矿木马(门罗币)样本分析
    Python守护进程和脚本单例运行
    iOS 支付宝支付
    iOS UI进阶-6.0 手势
    Objective-C中NSArray的基本用法示例
    UIImageView的图片居中问题
    iOS UI基础-19.0 UICollectionView
  • 原文地址:https://www.cnblogs.com/xj626852095/p/3648003.html
Copyright © 2011-2022 走看看