一文理解Redux及其工作原理
一、是什么
React
是用于構(gòu)建用戶界面的,幫助我們解決渲染DOM
的過程
而在整個應(yīng)用中會存在很多個組件,每個組件的state
是由自身進行管理,包括組件定義自身的state
、組件之間的通信通過props
傳遞、使用Context
實現(xiàn)數(shù)據(jù)共享
如果讓每個組件都存儲自身相關(guān)的狀態(tài),理論上來講不會影響應(yīng)用的運行,但在開發(fā)及后續(xù)維護階段,我們將花費大量精力去查詢狀態(tài)的變化過程
這種情況下,如果將所有的狀態(tài)進行集中管理,當(dāng)需要更新狀態(tài)的時候,僅需要對這個管理集中處理,而不用去關(guān)心狀態(tài)是如何分發(fā)到每一個組件內(nèi)部的
redux
就是一個實現(xiàn)上述集中管理的容器,遵循三大基本原則:
- 單一數(shù)據(jù)源
- state 是只讀的
- 使用純函數(shù)來執(zhí)行修改
注意的是,redux
并不是只應(yīng)用在react
中,還與其他界面庫一起使用,如Vue
二、工作原理
redux
要求我們把數(shù)據(jù)都放在 store
公共存儲空間
一個組件改變了 store
里的數(shù)據(jù)內(nèi)容,其他組件就能感知到 store
的變化,再來取數(shù)據(jù),從而間接的實現(xiàn)了這些數(shù)據(jù)傳遞的功能
工作流程圖如下所示:
根據(jù)流程圖,可以想象,React Components
是借書的用戶, Action Creactor
是借書時說的話(借什么書), Store
是圖書館管理員,Reducer
是記錄本(借什么書,還什么書,在哪兒,需要查一下), state
是書籍信息
整個流程就是借書的用戶需要先存在,然后需要借書,需要一句話來描述借什么書,圖書館管理員聽到后需要查一下記錄本,了解圖書的位置,最后圖書館管理員會把這本書給到這個借書人
轉(zhuǎn)換為代碼是,React Components
需要獲取一些數(shù)據(jù), 然后它就告知 Store
需要獲取數(shù)據(jù),這就是就是 Action Creactor
, Store
接收到之后去 Reducer
查一下, Reducer
會告訴 Store
應(yīng)該給這個組件什么數(shù)據(jù)
三、如何使用
創(chuàng)建一個store
的公共數(shù)據(jù)區(qū)域
import { createStore } from 'redux' // 引入一個第三方的方法 const store = createStore() // 創(chuàng)建數(shù)據(jù)的公共存儲區(qū)域(管理員)
還需要創(chuàng)建一個記錄本去輔助管理數(shù)據(jù),也就是reduecer
,本質(zhì)就是一個函數(shù),接收兩個參數(shù)state
,action
,返回state
// 設(shè)置默認值 const initialState = { counter: 0 } const reducer = (state = initialState, action) => { }
然后就可以將記錄本傳遞給store
,兩者建立連接。
如下:
const store = createStore(reducer)
如果想要獲取store
里面的數(shù)據(jù),則通過store.getState()
來獲取當(dāng)前state
console.log(store.getState());
下面再看看如何更改store
里面數(shù)據(jù),是通過dispatch
來派發(fā)action
,通常action
中都會有type
屬性,也可以攜帶其他的數(shù)據(jù)
store.dispatch({ type: "INCREMENT" }) store.dispath({ type: "DECREMENT" }) store.dispatch({ type: "ADD_NUMBER", number: 5 })
下面再來看看修改reducer
中的處理邏輯:
const reducer = (state = initialState, action) => { switch (action.type) { case "INCREMENT": return {...state, counter: state.counter + 1}; case "DECREMENT": return {...state, counter: state.counter - 1}; case "ADD_NUMBER": return {...state, counter: state.counter + action.number} default: return state; } }
注意,reducer
是一個純函數(shù),不需要直接修改state
這樣派發(fā)action
之后,既可以通過store.subscribe
監(jiān)聽store
的變化,如下:
store.subscribe(() => { console.log(store.getState()); })
在React
項目中,會搭配react-redux
進行使用
完整代碼如下:
const redux = require('redux'); const initialState = { counter: 0 } // 創(chuàng)建reducer const reducer = (state = initialState, action) => { switch (action.type) { case "INCREMENT": return {...state, counter: state.counter + 1}; case "DECREMENT": return {...state, counter: state.counter - 1}; case "ADD_NUMBER": return {...state, counter: state.counter + action.number} default: return state; } } // 根據(jù)reducer創(chuàng)建store const store = redux.createStore(reducer); store.subscribe(() => { console.log(store.getState()); }) // 修改store中的state store.dispatch({ type: "INCREMENT" }) // console.log(store.getState()); store.dispatch({ type: "DECREMENT" }) // console.log(store.getState()); store.dispatch({ type: "ADD_NUMBER", number: 5 }) // console.log(store.getState());
小結(jié)
- createStore可以幫助創(chuàng)建 store
- store.dispatch 幫助派發(fā) action , action 會傳遞給 store
- store.getState 這個方法可以幫助獲取 store 里邊所有的數(shù)據(jù)內(nèi)容
- store.subscrible 方法訂閱 store 的改變,只要 store 發(fā)生改變, store.subscrible 這個函數(shù)接收的這個回調(diào)函數(shù)就會被執(zhí)行
到此這篇關(guān)于一文理解Redux及其工作原理的文章就介紹到這了,更多相關(guān) Redux 工作原理內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
詳解關(guān)于React-Router4.0跳轉(zhuǎn)不置頂解決方案
這篇文章主要介紹了詳解關(guān)于React-Router4.0跳轉(zhuǎn)不置頂解決案,小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個參考。一起跟隨小編過來看看吧2019-05-05React使用useImperativeHandle自定義暴露給父組件的示例詳解
useImperativeHandle?是?React?提供的一個自定義?Hook,用于在函數(shù)組件中顯式地暴露給父組件特定實例的方法,本文將介紹?useImperativeHandle的基本用法、常見應(yīng)用場景,需要的可以參考下2024-03-03React Native:react-native-code-push報錯的解決
這篇文章主要介紹了React Native:react-native-code-push報錯的解決,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教2022-10-10React-native橋接Android原生開發(fā)詳解
本篇文章主要介紹了React-native橋接Android原生開發(fā)詳解,小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個參考。一起跟隨小編過來看看吧2018-01-01