Redux 进阶:拆分 reducer

❓ state 过于庞大怎么办

由于 Redux 应用中只有一个 store,所以,当应用的交互愈来愈复杂时,store 一定会变成一个很是庞大的对象。这时,咱们可使用 Redux 提供的 combineReducers() 方法将多个小的 reducer 组合成一个 rootReducer,而每一个小的 reducer 只关心本身负责的 action.type,由于在整个应用中,有些 state 之间是互不关联的,所以咱们能够拆分 reducer,不一样的 reducer 处理不一样的 action.typegit

假设如今有两个逻辑:一个计数器和一个 TODO。很明显这两个逻辑之间没有任何的联系,所以咱们能够拆分红两个 reducer,而后再组合起来传给 createStore()github

// 计数器 reducer
function counter(state = 0, action) {
  switch(action.type) {
    case 'INCREMENT':
      return state + 1;
    case 'DECREMENT':
      return state -1;
    default:
      return state;
  }
}

// TODO reducer
function todos(state = [], action) {
  switch(action.type) {
    case 'ADD_TODO':
      return state.concat([action.text]);
    default :
      return state;
  }
}

// 组合成一个 rootReducer
const rootReducer = combineReducers({
  counter,
  todos
});

// 根据 rootReducer 建立 store
const store = createStore(rootReducer)

console.log(store.getState());

结果

https://user-images.githubusercontent.com/22176164/39660627-c5f88b60-5075-11e8-93bc-b7ecc37fd49b.png

能够看到,store.getState() 中的 key 变成了子 reducer 的函数名,达到了拆分之间没有联系的 state 的目的。而 key 变成了子 reducer 的函数名的缘由是,在组合 reducer 时的写法:数据库

// 组合成一个 rootReducer
const rootReducer = combineReducers({
  counter,
  todos
});

这里传入给 combineReducers() 方法的是一个对象,这里使用了 ES6 的语法,即当对象的 keyvalue 同名时,能够省略 key,上面的写法至关于:设计模式

const rootReducer = combineReducers({
-  counter,
+  counter: counter,
-  todos
+  todos: todos
});

固然,key 是能够随意修改的,只是修改后,对于 state 的 key 也会有所不一样罢了。须要记住的是 combineReducers() 方法的参数是一个对象,对象的 value 是须要组合的 reducer,对象的key 对应的是 state 中的 key,返回的是一个组合后的 reducer 函数,能够像普通 reducer 同样传给 createStore() 方法建立 store。bash

与 React 结合后结果是这样的:架构

combinereducers

在 coding 以前

构建一个 Redux 应用以前,咱们应该先搭建好架构,也就是设计模式的那一套东西,在 coding 以前,不妨先停下来思考一下:函数

  • 代码文件的组织结构工具

    • 按角色组织
    • 按功能组织
  • state 树的设计性能

    • 一个模块控制一个 state 节点
    • 避免冗余数据:作到 state 的范式化,相似 SQL 关系型数据库。为解决范式化数据的性能问题,可使用 reselect 这样的工具提升性能。
    • 树形结构扁平,避免很深的层次
  • 肯定模块的边界:在理想状况下,咱们应该经过增长代码就能增长功能,而不是修改现有的代码。

下面是一个按功能组织的文件结构:spa

todoList/
  action.js            # 定义 action creators
  actionTypes.js       # 定义 action 类型
  index.js             # 把这个功能模块的文件导入,而后统一导出
  reducer.js           # 定义 reducer 如何处理 action
  views/               # 定义全部 React 组件,包括容器组件和展现组件
    component.js
    container.js
filter/
  action.js
  actionTypes.js
  index.js
  reducer.js
  views/
    component.js
    container.js
相关文章
相关标签/搜索