【sping揭秘】5、IOC容器(一)

 

OC容器实现过程

1、 容器启动阶段,读取配置文件,解析文件BeanDefinitionReader

2、 Bean 实例化阶段

 

 

关于BeanFactoryPostProcessor

 

插手spring的启动插入自己的逻辑,在第一阶段和第二阶段之间插入。。。

 

 

IOC容器中bean的操作

 

1、bean的实例化与BeanWarpper

 

容器在内部实现的时候,采用策略模式来决定如何初始化bean

 

 

策略模式:http://www.cnblogs.com/cutter-point/p/5259874.html

 

 

Spring一般使用cglib动态字节码技术实现创建一个bean实例

 

 

 

关于beanwarpper,就是一个用来包裹我们使用的类的类,用以节省我们操作的方便,这里通过一个案例展示

 

@Test
    public void testBeanWapper() {
        try {
            Object mo = Class.forName("cn.cutter.start.bean.MyObject").newInstance();
            //使用beanwrapper进行包裹类
            BeanWrapper moWrapper = new BeanWrapperImpl(mo);
            //设置值
            moWrapper.setPropertyValue("name", "cutter_point");
            moWrapper.setPropertyValue("phoneNumber", "有本事你打110");
            
            MyObject mo1 = (MyObject) mo;
            
            System.out.println("1->" + mo1.getName() + "\n1->" + mo1.getPhoneNumber());
            System.out.println("2->" + moWrapper.getPropertyValue("name") + "\n2->" + moWrapper.getPropertyValue("phoneNumber"));
            
        } catch (ClassNotFoundException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (InstantiationException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }
展示结果:

 

 

很方便,这样我们就免得写反射代码再去设置了

 

 

 

2、       InitializingBean

 

对象实现这个接口之后,spring会在实例化对象之后,立马调用这个方法,我们可以定义一个线程,在这个类实例化之后,定时清理缓存

 

package cn.cutter.start.bean;

import org.springframework.beans.factory.InitializingBean;
import org.springframework.stereotype.Component;

@Component
public class MyObject implements InitializingBean {
    private String name;
    private String phoneNumber;
    
    public MyObject() {
        System.out.println("MyObjec construct!");
    }
    
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
    public String getPhoneNumber() {
        return phoneNumber;
    }
    public void setPhoneNumber(String phoneNumber) {
        this.phoneNumber = phoneNumber;
    }
    @Override
    public void afterPropertiesSet() throws Exception {
        // TODO Auto-generated method stub
        System.out.println("we do initializingbean afterpropertiesset !");
    }
    
}

 

Spring运行结果

 

@Test
    public void test4() {
        ApplicationContext ctx = before();
        AwareTestBean awareTestBean = (AwareTestBean) ctx.getBean("awareTestBean");
        AwareTestBean awareTestBean2 = (AwareTestBean) awareTestBean.getBean("awareTestBean");
//        AwareTestBean awareTestBean3 = new AwareTestBean();
//        AwareTestBean awareTestBean4 = (AwareTestBean) awareTestBean3.getBean("awareTestBean");
        
        System.out.println(awareTestBean);
        System.out.println(awareTestBean2);
//        System.out.println(awareTestBean3);
//        System.out.println(awareTestBean4);
        
    }

不要在意里面的其他代码,注解掉也无所谓,不在这次的演示范围内,其实我们只需要运行第一行代码,也就是其中的before()函数,好吧,我再把before函数发出来

 

public ApplicationContext before() {
        ApplicationContext ctx = new ClassPathXmlApplicationContext("classpath:application-bean.xml");
        return ctx;
    }

 

展示结果:

先执行构造函数,然后执行afterPropertiesSet

 

 

posted @ 2018-03-19 21:04  cutter_point  阅读(204)  评论(0编辑  收藏  举报