七、通勤路上搞定 Spring 面试(2)

七、通勤路上搞定 Spring 面试(2)_第1张图片
面试题回顾:

  1. 如果要你实现 Spring IOC,你会注意哪些问题?
  2. BeanFactory 和 FactoryBean 有什么区别,Bean 是怎么加载出来的?
  3. AOP是什么,怎么实现,Spring 事务和它有什么关系?

前言

在上一篇文章中,我们了解了一个 IOC 需要拥有的基本功能,那接下来,我们需要了解下,IOC 容器是如何生产我们需要的 bean 的。

2.BeanFactory 和 FactoryBean 有什么区别,Bean 是怎么加载出来的?

这里面第一个问题可以说是较为基础的内容,我们可以单纯的从名字来区分他们的区别:

1. BeanFactory 是以 Factory 结尾,那他肯定属于工厂类型。
2. FactoryBean 是以 Bean 结尾,那他肯定是属于 bean 的一种。

BeanFactory 在第一个问题已经介绍过了,这里主要说一下 FactoryBean 。
FactoryBean 本身是一个接口,但同时,他也算是一种机制。IOC 容器里面创建的 bean 不一定都只是简单的反射生成出来,有可能是需要经过一系列复杂的操作后才能生成,而 FactoryBean 的作用便是为了让用户可以通过实现该接口定制实例化 Bean 的逻辑。如果我们的 bean 是通过 FactoryBean 的实现类获取,那有关这个 bean 的管理,Spring IOC 会将创建逻辑全部交给这个实现类来维护,IOC 本身只负责获取上的逻辑控制。

举一个例子,我们使用 Mybatis-Spring 的时候,不知道读者有没有考虑过我们写的 mapper 接口为什么可以当作具体的类使用,这里面其实就是使用了 FactoryBean 机制,Mybatis-Spring 通过继承 FactoryBean 接口实现相应的 mapper 实例化逻辑,来生成我们的 mapper 代理类,并将其存放到 IOC 容器当中,当我们使用 mapper 的方法时,最终是使用了由 FactoryBean 生产出来的 mapper 代理类的方法


理清 BeanFactory 和 FactoryBean ,现在我们来看看 bean 在 Spring 中是如何被创建出来的。
由上面章节我们得知创建 bean 的具体逻辑是在 AbstractAutowireCapableBeanFactory 中实现,那么接下来我们只需要跟着这个类的 createBean 方法走即可。
一般来说,我们主要是通过以下方法签名的 createBean 进行 bean 的创建

protected Object createBean(String beanName,
                            RootBeanDefinition mbd, 
                            @Nullable Object[] args)
			    throws BeanCreationException

在 Spring IOC 源码当中,一般核心业务逻辑会以 doXXX() 命名,因此,真正处理创建 bean 的方法是 doCreateBean(),我们可以从 createBean() 的源码中看到,如果是首次创建 bean ,最终都会进入 doCreateBean() 方法。至于 createBean() 方法,主要是做以下事情:

七、通勤路上搞定 Spring 面试(2)_第2张图片

创建 bean 的预处理运作完后,接下来就是具体的创建 bean 的逻辑了,我们来看看 doCreateBean() 方法做了什么:
七、通勤路上搞定 Spring 面试(2)_第3张图片

以上内容便是 IOC 容器创建 bean 的基础流程,读者有兴趣可以参照源码一起学习。

最后补充一点,通常我们调用 BeanFactory 接口的 getBean() 方法时,首先他会去从存储初始化完成的 bean 的缓存(map)中获取对应的 bean,获取不了的时候便会去调用 creatBean() 方法进行创建并将创建好的 bean 直接返回,也就是说,我们不需要主动调用 createBean() 方法来创建 bean ,只需要调用 getBean() 方法即可,无论有无创建,只要有符合的 bean 都会返回。

最后

有关创建 bean 的流程实际上很复杂,但是我这里只介绍了较为核心的步骤,代码贴的相对少一点,希望读者可以在阅读文章的同时浏览相关源码进行辅助,可以有效提高对这篇文章的理解,下面我们回到这个问题:

 BeanFactory 和 FactoryBean 有什么区别,Bean 是怎么加载出来的?

如果你们可以很流畅的回答这个问题,那么恭喜你,该章节的内容已经全部掌握,如果不行,希望可以回到对应问题讲解的地方,或者对某个不了解的点进行额外的知识搜索,尽量用自己组织的语言回答这些问题。

你可能感兴趣的:(Java,漫聊面试)