Flux架構(gòu)模式
在說flux模式之前坛悉,我們先說說mvc和mvvm模式
MVC模式
通過關(guān)注數(shù)據(jù)界面分離,來鼓勵改進應(yīng)用程序結(jié)構(gòu)际跪。也就是MVC將業(yè)務(wù)數(shù)據(jù)(model)與用戶界面(view)隔離敲街,用控制器(controller)管理邏輯和用戶輸入。
MVC模式中的三種角色
-
Model
Model負責(zé)保存應(yīng)用數(shù)組岗照,和后端交互同步應(yīng)用數(shù)據(jù),或校驗數(shù)據(jù)斧账。Model主要與業(yè)務(wù)數(shù)據(jù)相關(guān)谴返,與應(yīng)用內(nèi)交互狀態(tài)無關(guān)
-
View
View是Model的可視化,表示當前狀態(tài)的視圖咧织。前端View負責(zé)構(gòu)建和維護DOM元素嗓袱。更新Model的實際任務(wù)是在Controller上。用戶可以與View交互习绢,包括讀取和編輯Model渠抹,在Model中獲取或設(shè)置屬性值。一個view通常對應(yīng)一個model闪萄,所以在世實際開發(fā)過程中梧却,會面臨多個view對應(yīng)多個model的狀況
-
Controller
Controller負責(zé)連接view和model,model的任何變化會應(yīng)用到view中败去,view的操作會痛毆controller應(yīng)用到model中放航。
MVC的問題
MVC模式看上去沒有什么問題,但是它存在一個十分麻煩的缺點圆裕,這個缺點隨著你的項目越來越大广鳍,邏輯復(fù)雜的時候非常的明顯荆几,就是混亂的數(shù)據(jù)流動方式。
MVVM模式
MVVM的模式與MVC模式的最大區(qū)別在于數(shù)據(jù)綁定赊时,也就是說view的數(shù)據(jù)狀態(tài)的改變直接影響VM吨铸,反之依然。
MVC模式帶來問題的解決方案
如果渲染函數(shù)只有一個祖秒,統(tǒng)一放在Controller中诞吱,每次更新渲染頁面,這樣的話竭缝,任何數(shù)據(jù)的更新都只用調(diào)用重渲染就行房维,并且數(shù)據(jù)和當前頁面的狀態(tài)是唯一確定的。但是重渲染會帶來嚴重的性能問題于用戶體驗問題歌馍。
而Flux也是解決這類問題的一種方案
Flux模式
Flux的核心思想就是數(shù)據(jù)和邏輯永遠單向流動
眾所周知握巢,React提倡的是一種單向數(shù)據(jù)流,指的是父子組件之間的單向數(shù)據(jù)流松却。而Flux中的單向數(shù)據(jù)流則是在整體架構(gòu)上的延伸暴浦。在Flux應(yīng)用中,數(shù)據(jù)從action到dispatcher晓锻,再到store,最終到view的路線是單向不可逆的歌焦,各個角色之間不會像MVC模式中那樣存在交錯的連線
因為要實現(xiàn)單向數(shù)據(jù)流,所以在Flux模式中的dispatcher中定義了嚴格的規(guī)則來限定我們對數(shù)據(jù)的修改操作砚哆。只能通過dispatcher來修改store中的state独撇,所以同時,store中不能不暴露setter躁锁,強化數(shù)據(jù)修改的純潔性纷铣。
上面談到的如果渲染函數(shù)只有一個后,即每次數(shù)據(jù)的更新都會調(diào)用重渲染战转,會十分的影響性能搜立。在React中,通過Virtual DOM這個技術(shù)來進行優(yōu)化性能槐秧,因為每次重渲染的是內(nèi)存上的Virtual DOM啄踊,并由于PureRender保障從重渲染到局部渲染的轉(zhuǎn)換。
一個Flux應(yīng)用由三大部分組成dispatcher
,store
和view
- dispatcher負責(zé)分發(fā)事件
- store負責(zé)保存數(shù)據(jù)刁标,同時響應(yīng)事件并更新數(shù)據(jù)
- view負責(zé)訂閱store中的數(shù)據(jù)颠通,并使用這些數(shù)據(jù)渲染相應(yīng)的頁面
Flux的不足
雖然Flux的中心化控制十分優(yōu)雅。但是它最大的問題就是Flux的冗余代碼太多膀懈。雖然Flux源碼中幾乎只有dispatcher的實現(xiàn)顿锰,但是在每個應(yīng)用中東需要手動創(chuàng)建一個dispatcher的實例,而且在一個應(yīng)用中含有多個store。
基于Flux思想的Redux
Redux是基于Flux架構(gòu)思想的一個庫的實現(xiàn)撵儿,它主要的核心運作流程為:
Redux與Flux的區(qū)別
- Redux中只有一個store乘客,而Flux中有多個store來存儲應(yīng)用數(shù)據(jù),并在store里面執(zhí)行更新邏輯淀歇,當store變化的時候再通知controller-view更新自己的數(shù)據(jù),Redux是將各個store整合成一個完整的store,并且可以根據(jù)這個store來得到完整的state匈织,而且更新的邏輯也不再store中浪默,而是在reducer中。
- Redux沒有Dispatcher這個概念缀匕。它使用的是reducer來進行事件的處理纳决,reducer是一個純函數(shù)
(preState, action) => newState
,在Redux應(yīng)用中,可能有多個reducer乡小,每一reducer來負責(zé)維護應(yīng)用整體state樹中某一部分阔加,多個reducer通過combineReducers
方法合成一個根reducer,來維護整個state
如圖的比較
Flux:
Redux:
Redux設(shè)計和使用的三大原則
-
單一的數(shù)據(jù)源
在Redux的思想里,一個應(yīng)用永遠只有唯一的數(shù)據(jù)源满钟,使用單一數(shù)據(jù)源的好處在于整個應(yīng)用狀態(tài)都保存在一個對象中胜榔,我們隨時可以提取出整個應(yīng)用的狀態(tài)進行持久化,這樣的設(shè)計也為SSR提供了可能
-
狀態(tài)是只讀的
狀態(tài)是只讀的這個和Flux的思想相同,但是Redux中還限制了store的setter從而限制修改應(yīng)用狀態(tài)的能力湃番。在Redux中夭织,我們不會用代碼來定義一個store,而是通過reducer吠撮,通過當前觸發(fā)的action來對當前應(yīng)用的state進行迭代尊惰,這里沒有直接改變應(yīng)用的狀態(tài),而是返回了一個全新的狀態(tài)泥兰。
-
狀態(tài)修改均由純函數(shù)完成
在Flux中弄屡,是通過dispatcher的dispatch來觸發(fā)action,不僅產(chǎn)生了冗余代碼鞋诗,而且直接修改了store中的數(shù)據(jù)膀捷,無法保存每次數(shù)據(jù)變化前后的狀態(tài),在Redux中师脂,通過純函數(shù)reducer來確定狀態(tài)的改變担孔,因為reducer是純函數(shù),所以形同的輸入吃警,一定會得到相同的輸出糕篇,這樣的話,返回的是一個全新的state酌心,可以跟蹤每一次觸發(fā)action而改變狀態(tài)的結(jié)果成為了可能拌消,也就是可以達到炫酷的time travel 調(diào)試方法。
?? That's all~~ (github,歡迎star、follow)??