Spring的IOC面一文解析试中常问的那些核心题!

  

<>强广义的奥委会

  
      <李>奥委会(控制反转)控制反转,即“不用打电话过来,我们会打给你”。   
  

两种实现:依赖查找(DL)和依赖注入(DI)。

  

国际奥委会和DI, DL的关系(这个DL,阿瓦隆和EJB就是使用的这种方式实现的IOC):

  

一文解析Spring IOC面试中常问的那些核心题!

  
      <李>   

    DL已经被抛弃,因为他需要用户自己去是使用API进行查找资源和组装对象。即有侵入性。

      李   <李> DI是春天使用的方式,容器负责组件的装配。   
  
  

注意:Java使用DI方式实现国际奥委会的不止春天,包括谷歌的Guice,还有一个冷门的PicoContainer(极度轻量,但只提供IoC)。

     

<>强Spring的IoC

  

Spring的IoC设计支持以下功能:

  
      <李>依赖注入李   <李>依赖检查李   <李>自动装配李   <李>支持集合李   <李>指定初始化方法和销毁方法   <李>支持回调某些方法(但是需要实现春天接口,略有侵入)   
  

其中,最重要的就是依赖注入,从XML的配置上说,即裁判标签。对应春天RuntimeBeanReference对象。

  

<强>对国际奥委会于来说,最重要的就是容器。容器管理着豆的生命周期,控制着豆的依赖注入

  

那么,春天如何设计容器的呢?

  

春作者Rod Johnson设计了两个接口用以表示容器。

  
      <李> BeanFactory李   <李> ApplicationContext李   
  

BeanFactory粗暴简单,可以理解为就是个HashMap,关键是BeanName,价值是豆实例。通常只提供注册(把),获取(得到)这两个功能。我们可以称之为“低级容器”。

  

ApplicationContext可以称之为“高级容器”。因为他比BeanFactory多了更多的功能。他继承了多个接口。因此具备了更多的功能。

  
  

例如资源的获取,支持多种消息(例如JSP标记的支持),对BeanFactory多了工具级别的支持等待所。以你看他的名字,已经不是BeanFactory之类的工厂了,而是“应用上下文”,代表着整个大容器的所有功能。

     

该接口定义了一个刷新方法,此方法是所有阅读春源码的人的最熟悉的方法,用于刷新整个容器,即重新加载/刷新所有的bean。

  

当然,除了这两个大接口,还有其他的辅助接口,但我今天不会花太多篇幅介绍他们。

  

为了更直观的展示“低级容器”和“高级容器”的关系,我这里通过常用的ClassPathXmlApplicationContext类,来展示整个容器的层级UML关系。

  

一文解析Spring IOC面试中常问的那些核心题!

  

有点复杂?先不要慌,我来解释一下。

  

最上面的BeanFactory知道吧?我就不讲了。

  

下面的3个绿色的,都是功能扩展接口,这里就不展开讲。

  

看下面的隶属ApplicationContext粉红色的“高级容器”,依赖着“低级容器”,这里说的是依赖,不是继承哦。他依赖着“低级容器”的getBean功能。而高级容器有更多的功能:支持不同的信息源头,可以访问文件资源,支持应用事件(观察者模式)。

  

通常用户看到的就是“高级容器”。但BeanFactory也非常够用啦!

  

左边灰色区域的是“低级容器”,只负责加载Bean,获取Bean。容器其他的高级功能是没有的,例如上图画刷的刷新新豆工厂所有配置。生命周期事件回调等。

  
  

好,解释了低级容器和高级容器,我们可以看看一个奥委会启动过程是什么样子的。说白了,就是ClassPathXmlApplicationContext这个类,在启动时,都做了啥。(由于我这是interface21的代码,肯定和你的春天4。x系列不同)。

     

下图是ClassPathXmlApplicationContext的构造过程,实际就是Spring IoC的初始化过程。

  

一文解析Spring IOC面试中常问的那些核心题!

  

注意,这里为了理解方便,有所简化。

  

这里再用文字来描述这个过程:

  
      <李>   

    用户构造ClassPathXmlApplicationContext(简称CPAC)

      李

    Spring的IOC面一文解析试中常问的那些核心题!