來聊聊原始碼學習

黃軼發表於2018-06-07

現如今我們的開發工作並不會從零開始,往往會基於很多開源庫,就前端而言,構建工具我們會使用 webpack,MVVM 框架我們會使用 Vue、React 或者 Angular,這些開源工具幫助我們大大提升了生產效率。

通常我們學習一個開源專案的步驟都是先去閱讀它的官方文件,下載安裝後執行它的一些 demo 例項,然後在工作中去應用和踩坑。當我們對一個開源專案熟練使用並掌握後,再想去深入瞭解它就需要去閱讀它的原始碼了。

很多同學都嘗試學習過原始碼,目前業內也會有各種開源庫的原始碼解析文章,那麼今天我們也來聊聊原始碼學習這個事兒。

為什麼做

為什麼大家對原始碼解析這個事情樂此不彼呢,或者說我們為什麼要去學習原始碼呢,通常有以下幾個原因:

興趣驅動

這樣的同學往往是對技術非常熱愛,對未知技術的探索有著非常大的興趣,喜歡刨根問底。因此對於優秀的開源專案,他們都會非常願意花時間去探究它的實現原理,並且一旦弄明白後會有非常大的成就感。

技術驅動

這樣的同學往往是願意通過更多的學習來提升自己的技術能力。造輪子的技術含量比使用輪子的技術含量高,那麼研究輪子的實現原理,知道這個輪子是如何造出來的,也能在很大程度上提升自己的技術能力。而且一般研究的原始碼都是和工作相關,學習原始碼也可以很好輔助自己平時的工作開發。

坑驅動

這樣的同學會在使用開源專案過程中踩到一些坑,並且查閱資料無果後決定來看一下原始碼的實現,去找一下問題的原因。但是坑驅動學習原始碼的方式比較被動,往往只能學習到原始碼的冰山一角,效果不如前 2 者。

面試驅動

這樣的同學可能佔比最高,因為如今很多面試官都喜歡問一些技術的實現原理,那麼就會逼迫大家在面試前去學習平時工作中使用到技術棧的原理實現,但是這樣的學習是最被動的,很多人可能選擇去看一些原始碼解析的文章去死記硬背,而並沒有真正掌握原始碼實現的精髓。

什麼時候做

學習原始碼固然是件好事,但是如果在了不恰當的時機去學習可能會適得其反。有一部分同學對一個開源專案甚至都沒搞清楚是幹什麼的時候就開始去看原始碼了,如果是一些稍微複雜的開源專案,這樣的效率非常低下的,很大概率是時間浪費了什麼也沒有學到。

那麼什麼時候我們該學習原始碼呢,我認為你至少已經對這個開源專案的使用已經很熟練了,並且對它的設計思想,用來解決什麼問題等等都比較清楚的時候,為了進一步對它深入學習,就可以來看它的原始碼實現了。

怎麼做

那麼如何去學習原始碼就非常重要了,誠然學習原始碼是一定會花時間的,好的學習方法會大大提升學習效率,事半功倍。其實社群也有人推薦了一些學習原始碼的方式,比如說從原始碼早期的 commit 開始看,仿造一個小型輪子等等。這裡我結合自己看原始碼的經驗總結了幾個點。

全盤瞭解

首先你要對這個開源專案要有全盤的瞭解,知道它產生的背景,來解決什麼樣的問題。開始看原始碼前,先對它的原始碼目錄結構、程式碼執行入口、構建打包方式、最終產出的檔案等等有一個整體的瞭解。需要用一個全域性的視野去審視原始碼,切忌漫無目的的看原始碼。

問題驅動

在全盤瞭解的基礎上,就可以通過問題驅動去看原始碼了。以 Vue.js 為例,我們知道了它的核心思想是資料驅動 + 元件化,那麼我們就可以問自己,Vue 模板的資料是如何渲染到 DOM 上的,資料更新後模板是如何重新渲染的,元件化是如何實現的,模板到 render 函式如何編譯的等等。那麼每一個問題都可以值得我們針對性地去學習原始碼。問題驅動的方式和坑驅動不同的地方在於這個學習過程是主動的,自驅的,學到的東西會更加系統和全面;而坑驅動往往都會滿足於解決某個問題就停下了,學習會比較侷限。

主線優先

當我們通過問題驅動去看程式碼的時候,要牢記主線優先,所謂主線就是解決你這個問題核心流程中的程式碼。因為通常一個開源專案它的功能會很豐富,所以程式碼分支邏輯會有很多。而當我們帶著問題去看原始碼的時候,切忌像程式碼執行一樣把每個分支邏輯都去看一遍,我們要關心的就是主線部分。分支邏輯通常都是為了解決某些特定場景的問題,那麼如果想學習它的話就針對這個場景分析的時候再回來看即可。還是以 Vue.js 為例,比如我們在分析模板是如何驅動 DOM 渲染的,我們只要關心核心流程 init -> mount -> render -> update -> patch 這個過程的實現即可。那麼過程中遇到的初始化響應式物件這些分支邏輯,我們就可以先不看,因為當前分析的這個場景並不會有資料更新的部分,而這部分內容我們可以放到深入研究響應式原理的時候再看。

參與共建

我理想中的開源社群是有更多的人蔘與到開源專案的共建中,當我們給開源專案做貢獻的時候,會要求我們對原始碼的理解要更加深入。共建的方式有多種,比如可以給開源專案提個 pr;比如主動要求幫助解決開源專案現有的 issue;比如參與開源專案的文件編寫工作等等。我在研究 Vue.js 原始碼的過程中,也發現了一處原始碼的實現和文件不符的情況,於是提了 pr 對這個文件做了修復。通過共建的方式不僅僅可以幫助我們學習原始碼,也能增加成就感,一舉兩得。

閱讀技巧

當然,閱讀原始碼也是有很多技巧的,比如關鍵地方加斷點單步除錯、複雜函式看單元測試的輸入輸出、複雜邏輯通過畫圖輔助等等。

輔助資料

看懂原始碼實際上是一個有挑戰的過程,特別是一個複雜的開源專案。不同水平的人可能對原始碼的理解程度不一樣,這時候如果有一些別人分析好的優秀資料輔助我們學習原始碼,那麼效率會大大提升,理解起來也會更加容易。但是社群原始碼分析的資料很多,如何鑑別好的資料是非常有必要的。

Vue.js 原始碼學習

Vue.js 作為前端 MVVM 框架,已經被越來越多的公司使用,各類的原始碼分析文章也層出不窮。但是縱觀這些原始碼分析文章,大部分都是作者的一些學習筆記,通過給原始碼加一些註釋的方式,這種資料和直接去看原始碼差別並不大,因為原始碼也會在一些需要的地方加上註釋(除非你英文很差看不懂)。另一個比較大的問題就是比較零散,不夠系統和全面,如果想完整地去學習 Vue.js,這種東拼西湊的學習資料其實效果也並不好。但是社群也有做的不錯的,比如染陌同學的 learnVue,算是我見到的比較全面的 Vue.js 原始碼分析系列文章了。

由於我平時的工作專案就是利用 Vue.js 開發的,所以對 Vue.js 的研究也算比較多。我之前在慕課網上做過 2 門 Vue.js 的實戰課程,第一門《 Vue.js 高仿餓了麼》課程幫助大家入門了 Vue.js,第二門 《Vue.js 音樂 App》課程幫助大家在 Vue.js 的實戰方面做了進階。去年第二門課程出了後,我就在思考一件事,如何幫助我的學生在 Vue.js 這個方向繼續提升。於是我想到了做一門 《Vue.js 原始碼解析》的課程,幫助同學們修煉內功。

市面上還沒有原始碼解析類的視訊教學課程,我是第一個吃螃蟹的,原始碼課程的錄製難度要遠大於實戰課程的錄製,從開始準備到課程上線,經歷了半年以上的時間。為了把 Vue.js 的原始碼講明白,我結合了自己讀原始碼的經驗,把課程設計成由淺入深,分為核心、編譯、擴充套件、生態四個方面去講,並拆成了八個章節,如下圖:

enter image description here

除了課程視訊之外,我還寫了一本電子書,作為視訊的輔助教材。電子書是開源的,同學們可以免費閱讀,視訊是收費的,25+小時純乾貨課程,如果有需要的同學可以購買來學習,但請務必支援正版,請尊重作者的勞動成果。另外電子書和視訊都會持續更新和維護的,所以不必擔心 Vue.js 版本升級問題,以及後續也會在擴充套件章節增加新的內容,這些福利都是購買正版的學生才可以享有的喔~

結語

通常我們對一門技術的掌握程度,我把它分為了 5 個層次:會用;熟練掌握;瞭解其實現原理;知道為什麼這麼做;能提出更好的實現方式。相信大部分同學還在前 2 個層次,那麼對原始碼的學習,可以讓我們進階到第 3 個層次。如果你達到了第 4 個層次以上,那麼你已經是一個技術專家了。

希望同學們在學習原始碼的同時,不僅僅知其然,也能知其所以然。

相關文章