[关闭]
@Shel 2017-07-24T04:14:36.000000Z 字数 1522 阅读 642

Redux 重温

javascript react redux


纯函数

一个函数的返回结果只依赖于它的参数,并且在执行过程里面没有副作用,我们就把这个函数叫做纯函数。

不产生副作用,也就意味着我们不能操作DOM,也不能发Ajax请求,更不能直接更改传入的参数。
为什么要煞费苦心地构建纯函数?因为纯函数非常“靠谱”,执行一个纯函数你不用担心它会干什么坏事,它不会产生不可预料的行为,也不会对外部产生影响。不管何时何地,你给它什么它就会乖乖地吐出什么。如果你的应用程序大多数函数都是由纯函数组成,那么你的程序测试、调试起来会非常方便。

共享结构数据

此处输入图片的描述
修改数据的时候就把修改路径都复制一遍,但是保持其他内容不变,最后的所有对象具有某些不变共享的结构(例如上面三个对象都共享 content 对象)。
借助ES6的语法特性,想要实现共享数据结构的关键语法大致如下:

  1. let newState = { // 新建一个 newState
  2. ...oldState, // 复制 oldState 里面的内容
  3. title: { // 用一个新的对象覆盖原来的 title 属性
  4. ...oldState.title, // 复制原来 title 对象里面的内容
  5. text: '《React.js》' // 覆盖 text 属性
  6. }
  7. }
  8. // 这里利用了对象的浅复制

大多数情况下我们可以保持 50% 以上的内容具有共享结构,这种操作具有非常优良的特性,我们可以用它来优化渲染性能。

Reducer

这个函数被规定为一个纯函数,它接受两个参数,stateaction。如果没有传入 state 或者 state 是 null,那么它就会返回一个初始化的数据。如果有传入 state 的话,就会根据 action 来“修改“数据,但其实它没有、也规定不能修改 state,而是要通过共享结构数据把修改路径的对象都复制一遍,然后产生一个新的对象返回。如果它不能识别你的 action,它就不会产生新的数据,而是(在 default 内部)把 state 原封不动地返回。
reducer是不允许有副作用的。你不能在里面操作 DOM,也不能发 Ajax 请求,更不能直接修改 state,它要做的仅仅是 —— 初始化和计算新的 state。

Redux模式

共享的状态如果可以被任意修改的话,那么程序行为将非常不可预测,所以我们提高了修改数据的门槛:你必须通过store.dispatch执行某些允许操作,而且必须大张旗鼓的在action里面声明。
为了在修改数据的时候能够自动的刷新视图,我们加入了订阅者模式,可以通过store.subscribe订阅数据修改事件,每次数据更新的时候自动重新渲染视图。
然而直接的“重新渲染视图”有比较严重的性能问题,不能每一次修改都重头至尾的渲染一遍试图,因此可以在每个渲染函数的开头进行简单的判断避免没有被修改过的数据重新渲染。同时引入了“共享结构的对象”来帮我们解决数据问题。每一次修改数据对象,只会对需要修改的部分进行调整,渲染函数中的判断将会帮助我们跳过不需要重新渲染的部分,以优化性能。

  1. // redux的基本套路如下:
  2. // 定一个 reducer
  3. function reducer (state, action) {
  4. /* 初始化 state 和 switch case */
  5. }
  6. // 生成 store
  7. const store = createStore(reducer)
  8. // 监听数据变化重新渲染页面
  9. store.subscribe(() => renderApp(store.getState()))
  10. // 首次渲染页面
  11. renderApp(store.getState())
  12. // 后面可以随意 dispatch 了,页面自动更新
  13. store.dispatch(...)
  14. //套路结束,这里的redux模式和react.js一点关系都没有
添加新批注
在作者公开此批注前,只有你和作者可见。
回复批注