承上啟下
經歷了上一篇基礎的Promise講解後我覺得大家對於promise的基本用法和想法就有一定了解了。(就是一種承諾喲)
下面我們要去了解一下它的工作流程。
結合源碼與分析別人的常見實現進行理解
下面是別人實現的總源碼,(簡單一看就可以)
這是網上一份常見的Promise的源碼實現我會對這個進行一個分析。
(肯定有人問為什麼不自己實現一個? 解:省時、網上太多了、本質還是要了解思想)
話不多說開始咯
咱們先大體梳理一下實現的東西要能幹什麼?
first :
根據這個構造函數,我們需要實現兩個方法,resolve、reject方法
second :
我們要實現一個then方法,可以去根據不同狀態來執行不同的函數。
最基本的兩個內容我們已經確定了。
分析代碼
對代碼的分析在內容的注釋上大家不要遺漏哈!!!
第一段構造函數與狀態設定
自己實現與官方Promise執行的對比。大家可以看一下這個setTimeout導致的執行順序問題。所以閱讀別人對各種功能實現時要學會對照的去看。
到這裡夥伴們已經了解了我們new 一個構造函數時都會做哪些事情。
1:對promise實例定義一個狀態,值為PENDING。2:給promise實例定義一個存放值的空間。3:設置一個發布列表,在以後的指定時間發布其中的事件。4:通過bind函數將callback柯裡化,使callback執行時調用對應的resolve與reject方法,並執行callback
第二段 resolve reject then方法的分析
為什麼先說這三個方法。
因為resolve、reject是核心方法,不說都不行,可是resolve與reject完成要做的事情必須是then方法指定的所以三個方法之間關係密切。
到這裡我們大體梳理清楚,resolve、reject、then方法的用處。
提一嘴 reject方法沒有執行done函數會導致以下情況
一:在new promise實例過程中執行的callback函數,在函數執行的過程中肯定會調用resolve或者reject(兩個都調用也可能)。當調用了resolve方法之後會改變promise的狀態,存放結果。表示任務完成,執行done函數。(reject就不再來一遍了)
二:then方法的執行事件與resolve方法沒有任何先後順序可言。隨心所欲誰在前面都不一定。在resolve(reject)之前執行,就註冊一下要執行的事件。在resolve(reject)之後執行就直接執行就可以了,並且不要註冊。
第三段 具體是怎麼執行的呢?聊聊done與handle
同學們按照代碼執行的順序,我們應該先去看done方法。然後再看handle所以辛苦一下,先向下一點找到可愛的done方法。
這一段我已經把handle與done方法說完了。主要是為了鏈式調用。才會設計的這樣子。所以鏈式調用還是很搶手的一個功能。
自己也可以嘗試的去實現一下符合promise規範的promise功能。
親! 學習完要思考
不知道看到這裡大家對網上常見的promise源碼實現有一種什麼樣的感覺???
我先說說我的感覺
看過源碼(抱歉我的智商是在有限,短時間內是真的看不懂啊),覺得源碼做的要合理太多了。看不懂我都覺得合理。。。。不是對強者的過分崇拜,而是真的很合理。網上常見的實現,只是單單的實現了功能,這樣的promise只適合有一定promise經驗並且守規矩的人使用。為什麼這麼說???
一:這樣實現的promise,狀態可以隨時人為的更改,對外暴露,沒有設置為私有屬性。二:為了方便,選擇把方法設置在原型鏈上,導致無法使用私用變量。三:reject的執行不足,只是對resolve進行合理的使用。雖然我這麼說,我也實現不出來,寫出這些的人還是比我厲害很多。promise的源碼則是(某個版本的,版本號我不記得了)把resolve、reject、all、race,handle方法,都放在構造函數內。把catch、then、chain方法放在原型上。
有圖為證,字面意思應該是這個意思,我覺得我沒想錯。
在改變promise的狀態也好、value也好。都在頻繁的使用PromiseSet方法來設置屬性,對方法進行封裝,並且方便狀態的管理,附加合理的容錯。
對比源碼之後,覺得自己雖然流程大體了解,但是這種精密而且優雅的方式,是短時間內很難去掌握的。promise的源碼當然會堅持看下去,網上能把promise按照規範實現一遍的人已經很厲害了。我雖然覺得還有地方可以修改,但是我比他們還差得遠(這種感覺就有點像:我不上,我就比比),要向他們學習,照這他們去努力。
別說了 喝雞湯吧
前端的學習之路還很漫長,我看過的(僅僅是看過的)源碼半隻手就都數的過來。還是堅信堅持下去,自己就變得很棒。每個人都是從控制流語句學過來的,邏輯也不過是複雜的控制流程(還涉及高端的算法與設計模式),堅信自己一定可以成功!!!一起努力吧 每一個前端er(boy and girl)。所以一切源碼層面看不懂、不理解都可以歸結為看得少、想得少、理解的少。(和你的智商沒有任何關係喲)
下期預告
下一篇就是理解異步之美的終點篇了。異步的美好在於這種神奇的思想。抓住思想的尾巴,不被技術束縛,嘿嘿嘿。
要開新課題了。課題應該是圍繞著vue-router的源碼進行學習。一個與大家分享學習過程的周期性文章。盡情期待!!!