1. 爲了擴展和調優:掌握框架的工做流程和原理編程
2. 爲了提高本身的編程技能:學習他人的設計思想、編程技巧app
方法一:框架
1)掌握研究的對象和研究對象的核心概念:搞明白框架都能作什麼,是怎麼作的。eclipse
好比咱們要研究Spring的源碼,那麼研究的對象就是Spring,Spring的核心概念有IOC、DI、AOP等,那麼咱們就須要搞明白這些核心概念能作什麼,是怎麼作的maven
2)從總體到部分ide
首先要弄清楚總體是由哪些部分組成起來工做的,而後再去研究各個部分是怎麼作的。好比咱們如今研究Spring IOC,就要先弄清楚IOC由建立bean定義、註冊bean定義、bean工廠幾部分組合起來工做的,而後再去研究這幾個部分是怎麼作的函數
3)找到入口,先理清楚主幹流程,而後再去研究各個流程的細節學習
好比咱們要研究Spring是怎麼加載xml配置文件去建立實例的,那麼咱們就須要找到入口,從入口進去之後先不要急着看具體的實現細節,要先理清楚主方法裏面大概作了哪些事,而後再去看各個方法是怎麼作的測試
4)多折騰、勤折騰this
研究完源碼之後,知道源碼能作什麼、是怎麼作的了,那麼就能夠寫一些代碼去測試他是否是確實能作到。或者知道源碼有一些擴展點,就本身嘗試去擴展一下
方法二:
1)掌握研究的對象和研究對象的核心概念:搞明白框架都能作什麼,是怎麼作的。
好比咱們要研究Spring的源碼,那麼研究的對象就是Spring,Spring的核心概念有IOC、DI、AOP等,那麼咱們就須要搞明白這些核心概念能作什麼,是怎麼作的
2)本身動手嘗試去實現。
3)本身實現完之後,再去對比看源碼裏面是怎麼實現的,源碼裏面爲何要那樣去實現,有什麼好處,學習源碼裏面好的地方
前面的兩種方法,我的比較推薦方法一,由於每一個人的水平不同,方法一相對方法二來講要簡單一點
前面已經介紹了兩種學習源碼的方法,那麼怎麼深刻到源碼裏面去看別人是怎麼作、選擇性的去看某一部分源碼是怎麼作的呢?針對不一樣的狀況,有下面的方法:
第一種方式:
剛剛接觸到一個新框架,徹底不知道源碼是幹什麼的,這種狀況就得找到官方文檔裏面的使用示例找到入口,而後一步一步的去調試拿到整個調用棧,拿到整個調用棧之後就知道主幹流程了,再去分析本身感興趣的部分是怎麼實現的就比較簡單了(比較費時)
第二種方式:
通過 學習源碼的方法的方法一中的第 1)步 分析,知道源碼裏面要作某一件事,那就找到官方文檔裏面的使用示例找到入口,而後找到作某一件事的地方,打個斷點,直接debug到作這件事地方拿到調用棧去分析,看都通過了哪些處理,而後去分析本身感興趣的部分是怎麼實現的。
好比IOC容器加載配置文件建立bean實例時必定會有註冊bean定義的步驟,那麼咱們就先根據類的繼承體系找到註冊bean定義的類和對應的方法的實現的地方,在裏面打個斷點,直接debug到註冊的方法的斷點的地方時就能獲取到調用棧了,而後再根據調用棧分析Spring要完成根據xml配置建立bean實例都有哪些類參與進來。
下面就來舉例說明:
首先從官方文檔能夠得出以下使用示例:
官方文檔:
使用示例:
ApplicationContext context = new ClassPathXmlApplicationContext("application.xml");
而後進入ClassPathXmlApplicationContext裏面
咱們知道IOC容器的工做過程是加載xml、解析xml獲得bean定義、把bean定義註冊到bean工廠裏面、bean工廠根據bean定義建立bean實例,那麼咱們就根據ClassPathXmlApplicationContext的繼承體系先找到哪一個類裏面持有bean工廠,找到持有bean工廠的地方之後先看有沒有註冊bean定義相關的方法,根據繼承體系尋找,最終發如今父類AbstractRefreshableApplicationContext裏面持有Bean工廠DefaultListableBeanFactory:
/** Bean factory for this context. */ @Nullable private DefaultListableBeanFactory beanFactory;
經過在AbstractRefreshableApplicationContext裏面查找,沒有找到註冊bean定義相關的方法,那麼咱們就看DefaultListableBeanFactory的裏面有沒有註冊bean定義相關的方法,最終發現DefaultListableBeanFactory裏面果真有註冊bean定義的方法registerBeanDefinition
@Override public void registerBeanDefinition(String beanName, BeanDefinition beanDefinition) throws BeanDefinitionStoreException {
經過查看DefaultListableBeanFactory繼承體系,咱們能夠看到DefaultListableBeanFactory實現了BeanDefinitionRegistry這個接口來實現bean定義註冊
那麼咱們就在registerBeanDefinition(String beanName, BeanDefinition beanDefinition)方法裏面打個斷點,而後debug運行前面的示例代碼到這裏:
到這裏咱們就能拿到整個調用棧了:
拿到調用棧之後,咱們就能夠來分析Spring是怎麼加載xml、解析xml獲取bean定義、註冊bean定義到bean工廠的了
那麼怎麼來具體分析調用棧呢?
主要看調用棧(看從開始到註冊bean定義這件事情)用到了哪些類的哪些方法,看傳參。工做是如何分配、分工協做完成的。
看傳參重點是看輸入的參數(如xml配置文件的路徑)在這些類中是怎麼變化的(代碼的本質其實就是對輸入數據的各類處理獲得最終想要的結果),從而知道每個類是幹什麼用的。分析完整個調用棧之後,想要了解哪一部分就點擊對應的調用棧去分析就好了。
從調用棧能夠看到要加載xml、解析xml獲取bean定義、註冊bean定義到bean工廠這些事須要三個類依次參與進來:
說明:
方法裏面含有<init>的表示是在構造函數進行初始化,方法裏面帶有(AbstractApplicationContext).refresh()的表示調用的是AbstractApplicationContext父類的refresh()方法,其餘的相似
1)ClassPathXmlApplicationContext:初始化、準備BeanFactory
2)XmlBeanDefinitionReader:輸入的xml配置文件路徑的字符串到Document的轉換
3)DefaultBeanDefinitionDocumentReader 解析Document獲得bean定義持有器BeanDefinitionholder
4) 後面的步驟就是把BeanDefinitionholder裏面的Bean定義註冊到Bean工廠裏面
前提:在eclipse裏面導入了源碼或者用maven引入了源碼的依賴
1. 查找源碼的類的快捷鍵
Ctrl+Shift+T 而後輸入要看的類
2. 查看一個類繼承了哪些類的以及有哪些子類
選中要查看的類,右鍵-選擇Open Type Hierarchy(打開類的繼承體系)
public interface ApplicationContext extends EnvironmentCapable, ListableBeanFactory,HierarchicalBeanFactory,MessageSource,ApplicationEventPublisher, ResourcePatternResolver
查看繼承了哪些類:
查看有哪些子類:
選中部分裏面對應的成員:
3. 查看一個類都有哪些子類
選擇要看的類 而後Ctrl+T