redux状态管理器,实质上就是一个单例模式。咱们来实现一个简单的redux模型,实现以前咱们要先熟悉它的用法。 redux
下面咱们按照这个思想来想一想怎么作。 咱们来抽象一下,提取出最核心的思想,动用鬼斧神工画个图:数组
用文字来描述一下,一个惟一的仓库里,有一个私有属性state,仓库由门卫大哥进行管理,全部对state的操做都要通过门卫大哥,外面的人无权直接对state进行操做,若是有进行订阅,则在状态改变后收到状态改变事件。好了,咱们按照这个思想来开始code吧函数
const state={ a: 1 }
function createStore(){ const state={ a: 1 } }
function createStore() { let state={ a:1 }; function getState() { return state //此处直接将state返回,会使state引用地址暴露,从而被引用对象改变值 } return { getState } } let store = createStore() // 建立一个仓库 let state = store.getState() // 获取状态state console.log(store.getState()) // 输出{ a: 1 } state.a = 2 //将state a的值设置为2 console.log(state) // 输出为{ a: 2 } console.log(store.getState()) // 此时仓库中state的值也改变了,输出为{ a: 2 }
因此咱们将第六行 return state
替换为 return JSON.parse(JSON.stringify(state))
能够避免这个问题。优化
'use strict' function createStore() { let state; function getState() { return JSON.parse(JSON.stringify(state)) } function dispatch(action) { // 分发 state = reducer(state,action) // 接收当前 State 和Action做为参数,返回一个新的 State } dispatch({ type: '@@INIT' }) // 在建立仓库的时候,初始化state的值 return { getState, dispatch } } let initState = { count: 0 } //处理器,接收二个参数 ,接收老状态和action,返回新状态 function reducer(state = initState, action) { // 若是state没有值,默认值为initState //判断动做的类型 switch (action.type) { case 'ADD_TODO': return { ...state, count: action.number }; //...state解构state全部属性,count: action.number覆盖前面的值 default: return state; } } let store = createStore() // 建立一个仓库 let state = store.getState() // 获取状态state let action = { type: 'ADD_TODO', number: 1 }; store.dispatch(action); // 派发一个action,改变state的状态 console.log(store.getState()) // 输出{ count: 1 }
diapatch中执行咱们定义的reducer处理器函数,增删改查。例子演示了先建立一个仓库,在建立新仓库的时候初始化了state。而后diapatch一个action:ADD_TODO,执行的处理是改变count的值,返回一个新的state对象,最后咱们能够看到输出,原来的state在初始化后变成{ count: 0 },又在ADD_TODO后变成了{ count: 1 }。spa
reducer函数是咱们在使用redux时须要本身定义的处理函数。code
至此,咱们已经实现了建立一个仓库,而且能够自定义一些处理函数对state进行操做。还缺了什么呢?在实际项目中,状态改变后咱们的大部分的组件须要当即获得新的状态,而后根据状态改变做出不一样的处理。也就是说组件对state进行一个监听,一旦state发生改变,立马通知到对应的组件。让咱们来继续实现吧。。。cdn
function createStore() {
let state;
let listeners = [];
function getState() {
return JSON.parse(JSON.stringify(state))
}
function dispatch(action) { // 分发
state = reducer(state,action); // 接收当前 State 和Action做为参数,返回一个新的 State
listeners.forEach(listener => listener()) // 一旦状态改变,触发全部的监听函数,这里须要优化,只有相关状态改变才须要触发
}
function subscribe(listener){ // 订阅,若是需监听状态变化,将监听函数传过来
listeners.push(listener); // 保存监听函数到监听数组
return function () { // 返回取消订阅的函数
listeners = listeners.filter(item => item != listener); // 过滤监听函数
}
}
dispatch({ type: '@@INIT' }); // 在建立仓库的时候,初始化state的值
return {
getState,
dispatch,
subscribe
}
}
/*这里是分割线,上面一部分是仓库定义,下面部分是使用方法*/
let initState = {
count: 0
}
//处理器,接收二个参数 ,接收老状态和action,返回新状态
function reducer(state = initState, action) { // 若是state没有值,默认值为initState
//判断动做的类型
switch (action.type) {
case 'ADD_TODO':
return { ...state, count: action.number }; //...state解构state全部属性,count: action.number覆盖前面的值
default:
return state;
}
}
let store = createStore() // 建立一个仓库
let action = { // 定义一个action
type: 'ADD_TODO',
number: 1
};
let unADD = store.subscribe(function(){ // 监听状态改变
console.log('状态改变了,如今的state为:') // 状态改变了,如今的state为:
console.log(store.getState()) // { count: 1 }
})
store.dispatch(action); // 派发一个action,改变state的状态
复制代码
铛铛铛~,咱们的redux基本模型就作好了,有什么不懂的能够提问哟~对象