傳送門spring
BeanFactory
加載 XML
BeanFactory bf = new XmlBeanFactory(new ClassPathResource("applicaitonContext.xml"));
Ps:由於我是跟着《Spring源碼深度解析》學習的,而這本書出版在13年9月,這一種方法在新的Spring
版本中已經廢棄掉了,取而代之的是下面的方法;但既然學了,那就仍是記錄一下,學習一下開發者的思想也是不錯的.數組
ApplicationContext
加載 XML
ApplicationContext context = new ClassPathXmlApplicationContext("applicationContext.xml");
上述二者都是經過加載XMl
配置文件的方式加載Bean
,然後者是前者的擴展,提供了更多的功能,即ApplicationContext
擁有BeanFactory
的所有功能,在絕大多數的"典型的"企業應用和系統,ApplicationContext
都優先於BeanFactory
.app
BeanFactory
是延遲加載,若是一個Bean
當中存在屬性沒有加載,會在第一次調用getBean()
方法的時候報錯,而ApplicationContext
會在讀取Xml
文件後,若是配置文件沒有錯誤,就會將全部的Bean
加載到內存中,缺點就是在Bean
較多的時候比較佔內存,程序啓動較慢.函數
Spring
容器加載中最重要的兩個類XmlBeanFactory
繼承自DefaultListableBeanFactory
,然後者是整個Bean
加載的核心部分,是Spring
註冊及加載Bean
的默認實現,而XmlBeanFactory
使用了自定義的Xml
讀取器XmlBeanDefinitionReader
,實現了個性化的BeanDefinitionReader
讀取.學習
主要負責Xml
文件的讀取、解析和註冊功能this
上面的兩種方法的處理大體相同,讓咱們經過時序圖看看二者在加載時的區別:code
BeanFactory bf = new XmlBeanFactory(new ClassPathResource("applicaitonContext.xml"));
粗略時序圖:xml
首先,將applicationContext.xml
用ClassPathResource
進行封裝獲得Resource
資源,Resource
接口將全部的資源文件統一處理,當經過Resource
相關類完成了對配置文件的封裝以後,就由XmlBeanDefinitionReader
進行讀取和解析.對象
ApplicationContext context = new ClassPathXmlApplicationContext("applicationContext.xml");
粗略時序圖:繼承
附上ClassPathXmlApplicatioContext
構造函數的源碼:
public ClassPathXmlApplicationContext(String[] paths, Class<?> clazz, ApplicationContext parent) throws BeansException { super(parent); Assert.notNull(paths, "Path array must not be null"); Assert.notNull(clazz, "Class argument must not be null"); this.configResources = new Resource[paths.length]; //建立資源數組 private Resource[] configResources; for (int i = 0; i < paths.length; i++) { this.configResources[i] = new ClassPathResource(paths[i], clazz); } refresh(); //解析工做,ClassPathXmlApplicatioContext繼承來自AbstractApplicationContext中的方法 }
首先,一樣是封裝配置文件,但封裝完成以後並無直接進行讀取,而是調用了refresh()
方法(這個方法裏面進行了不少操做,擴展的功能幾乎是在這裏面實現的),refresh()
方法中的obtainFreshBeanFactory()
方法負責初始化BeanFactory
,並對XMl
文件讀取,讀取的核心實現是該方法中調用的refreshBeanFactory()
方法,這個方法再調用圖中的loadBeanDefinitions(beanFactory)
方法(因爲板面緣由,沒有畫出),而後在其中建立XmlBeanDefinitionReader
對象,再將最初封裝的資源文件數組進行依次讀取並解析.
兩者在後面的Xml
解析工做都幾乎是同樣的,都採用了SAX
解析,區別就在於解析以前的準備和解析以後的完善工做.