FactoryBean,InitializingBean使用

 

  Spring中有两种类型的Bean,一种是普通Bean,另一种是工厂Bean,即FactoryBean。工厂Bean跟普通Bean不同,其返回的对象不是指定类的一个实例,其返回的是该工厂Bean的getObject方法所返回的对象。

使用场景:1、通过外部对类是否是单例进行控制,该类自己无法感知 2、对类的创建之前进行初始化的操作,在afterPropertiesSet()中完成。

实例一: 

基础类:Student.java

  
  
  
  
  1. public class Student { 
  2.     private int    id; 
  3.     private String name; 
  4.  
  5.     public int getId() { 
  6.         return id; 
  7.     } 
  8.  
  9.     public void setId(int id) { 
  10.         this.id = id; 
  11.     } 
  12.  
  13.     public String getName() { 
  14.         return name; 
  15.     } 
  16.  
  17.     public void setName(String name) { 
  18.         this.name = name; 
  19.     } 
  20.  

工厂类:StuFactory.java

  
  
  
  
  1. public class StuFactory implements FactoryBean, InitializingBean { 
  2.  
  3.     public void afterPropertiesSet() throws Exception { 
  4.         System.out.println("student class initialized."); 
  5.     } 
  6.  
  7.     public Object getObject() throws Exception { 
  8.         return new Student(); 
  9.     } 
  10.  
  11.     public Class getObjectType() { 
  12.         return Student.class
  13.     } 
  14.  
  15.     public boolean isSingleton() { 
  16.         return true
  17.     } 

注入到配置文件中:

  
  
  
  
  1. <?xml version="1.0" encoding="UTF-8"?> 
  2. <beans xmlns="http://www.springframework.org/schema/beans" 
  3.     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:lang="http://www.springframework.org/schema/lang" 
  4.     xsi:schemaLocation=" 
  5. http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd 
  6. http://www.springframework.org/schema/lang http://www.springframework.org/schema/lang/spring-lang-2.5.xsd"> 
  7.  
  8.     <bean id="stuFactory" class="com.alibaba.spring.StuFactory"> 
  9.     </bean> 
  10. </beans> 

测试:

  
  
  
  
  1. public class StuFactoryTest { 
  2.     @Test 
  3.     public void test1() throws Throwable { 
  4.         ApplicationContext context = new ClassPathXmlApplicationContext("applicationContext.xml"); 
  5.         Student stuFactory1 = (Student) context.getBean("stuFactory"); 
  6.         Student stuFactory2 = (Student) context.getBean("stuFactory"); 
  7.  
  8.         System.out.println(stuFactory1 == stuFactory2); 
  9.     } 

测试结果:

  
  
  
  
  1. student class initialized. 
  2. true 

【注意】

1、返回的是getObject()中说明的类型,而不是创建工厂的类型,与普通的javabean不一样

2、创建出来的对象是否属于单例由isSingleton中的返回决定。

实例二:

FactoryBeanDemo.java

  
  
  
  
  1. public class FactoryBeanDemo implements FactoryBean { 
  2.     private String name; 
  3.  
  4.     public void setName(String name) { 
  5.         this.name = name; 
  6.     } 
  7.  
  8.     public Object getObject() throws Exception { 
  9.         if ("date".equals(name)) 
  10.             return new Date(); 
  11.         else 
  12.             return new String("这是一个字符串!"); 
  13.     } 
  14.  
  15.     public Class getObjectType() { 
  16.         return "date".equals(name) ? Date.class : String.class
  17.     } 
  18.  
  19.     public boolean isSingleton() { 
  20.         return false
  21.     } 

配置文件:

  
  
  
  
  1. <bean name="myFactoryBean" class="com.alibaba.spring.FactoryBeanDemo" /> 
  2.  
  3. <bean name="myFactoryBean1" class="com.alibaba.spring.FactoryBeanDemo"> 
  4.     <property name="name" value="date"></property> 
  5. </bean> 

测试:

  
  
  
  
  1. Resource res = new ClassPathResource("applicationContext.xml"); 
  2.       BeanFactory factory = new XmlBeanFactory(res); 
  3.       System.out.println(factory.getBean("myFactoryBean").getClass()); 
  4.       System.out.println(factory.getBean("myFactoryBean1").getClass()); 
  5.       System.out.println("====================================="); 
  6.       System.out.println(factory.getBean("&myFactoryBean").getClass()); 
  7.       System.out.println(factory.getBean("&myFactoryBean1").getClass()); 

由此可见,通过使用FactoryBean,我们可以得到不同类型的对象实例。这也就是我们在AOP中通过设置calss为ProxyFactoryBean可以返回不同类型的业务对象的原理。在实际应用中若能灵活使用FactoryBean,则可以给应用程序增加很多的魔幻功能。

测试结果:

  
  
  
  
  1. class java.lang.String 
  2. class java.util.Date 
  3. ===================================== 
  4. class com.alibaba.spring.FactoryBeanDemo 
  5. class com.alibaba.spring.FactoryBeanDemo 

一个小窍门:
FactoryBean还藏有一个技巧,也就是在我们实际需要返回FactoryBean实例时,应该怎么办。也就是我们在应用程序中需要通过容器得到一个FactoryBean。此时,需要使用特殊的方式,即在bean的名称前加上一个特殊符号“&”即可。即:System.out.println(factory.getBean("&myFactoryBean").getClass());


 

 

 

 

你可能感兴趣的:(职场,FactoryBean,休闲)