资讯专栏INFORMATION COLUMN

Redux概念之二: Redux的三大原则

dingda / 729人阅读

摘要:就是应用程序领域的状态,它是类型中的模型的设计的概念,这设计是由架构而来的,在原本的架构中是允许多个的结构,简化为只有单一个。的设计中是与中的相比,它们之间有一些类似的设计。

Redux里的强硬规则与设计不少,大部份都会与FP(函数式程序开发)、改进原本的Flux架构设计有关。Redux官网文档上的三大基本原则,主要是因为有可能怕初学者不理解Redux中的一些限制或设计,所以先写出来说明,这里面也说明了Redux的设计原理基础是如何,所以强烈建议所有的初学者一定要彻底地理解这三大原则中的意义,多看几遍,对日后的学习会很有帮助。以下分别说明,主要以原文的标题与内容说明,尽可以说明的比较清楚些。

单一真相来源

你的整个应用中的state(状态),会存储在单一个store(存储)之中的一个对象树状结构里。

Redux中只有用单一个对象大树结构来的存储整个应用的状态,也就是整个应用中会用到的数据,称之为store(存储)。但要注意的是store(存储)并不是只有单纯的数据而已。store就是应用程序领域的状态,它是类型MVC中的Model(模型的)设计的概念,这设计是由Flux架构而来的,在原本的Flux架构中是允许多个store的结构,Redux简化为只有单一个。

Redux的单一个store的设计有一些好处,对开发者来说,它可以容易调试与观察状态的变化,状态存储于对象树状结构中,也很容易作到重作/复原(Undo/Redo)的功能。因为只有一个store,但如果store里要储放多个不同的状态对象,以及每次的更动数据,自然就会变成了对象树状结构(object tree)。

此外,如果你想要从store中取出目前的状态数据,可以用store的getState()方法。

状态是唯读的

唯一能更动状态的是发送一个action(动作),action是一个描述"发生了什么事"的纯对象

这里指的"状态",是上面说的储放在store中的状态数据,你"不能直接"对其中的状态数据更动,只能"间接"地作这事。这与原先的React中的statesetState的概念有点像,Redux的意思是你不能直接更动store里面所记录的状态值,只能"间接"地透过发送action对象来叫store更动状态。"间接"地更动状态是一个很关键的设计,这是Flux中单向数据流的重点之一,这对于每个动作发生,最终会影响到什么状态上的更动,一个接一个的顺序等等的一种严格的设计。

你可能会认为"状态既然是唯读",直接与间接有什么差异,"唯读"不就代表完全不能更动,这语句是不是有误?

"唯读"当然就是完全不能更动的意思没错,所以状态对象的更动是并不是在原先的状态对象上变动它,而是由原先状态对象因为动作的加入后,产生一个全新的状态对象,用这全新的状态对象来取代原先的状态对象而已。这在真实世界中或许很难拿比喻来说明,但在软体世界中这很可以很容易达成。

"发生了什么事"这句,是代表每个action都会有一个type(类型),代表这个动作是要作什么用的,或是现在是发生了什么,例如是要新建一笔什么数据,或是删除整个数据等等,动作对象除了要说明它是要作什么之外,也需要包含所影响的数据。

发送一个action(动作),使用的是store.dispatch(action)语法样式,下面这个例子就是一个要更动状态的代码:

store.dispatch({
  type: "COMPLETE_TODO",
  index: 1
})

中间的那个纯对象,就叫作action(动作),它是一个单纯用于描述发生了什么事与相关数据的纯对象:

{
  type: "COMPLETE_TODO",
  index: 1
}

还记得我们在React中的statesetState方法的设计吗?state也是不能直接更动的,一定要透过setState方法才能更动它。那这是为什么呢?因为setState不光只是更动state值,它还要作重新渲染的动作,React需要比对目前的状态,与即将要变动的状态,这样才能进移动新渲染的工作。Redux的设计中store是与React中的state相比,它们之间有一些类似的设计。

更动只能由纯函数来进行

要指示状态树要如何依actions(动作)来作改变,你需要撰写纯粹的归纳函数(reducers)

Redux中的reducer的原型会长得像下面这样,你可以把它当作就是 之前的状态 + 动作 = 新的状态 的公式:

(previousState, action) => newState

注: 你可以参考Redux中Reducers这一章的内容,里面有实例。

不过,Redux中的reducer一定是纯函数(pure function),也就是不能有副作用的函数。因此由reducer所产生的新状态,并不是直接修改之前的状态而来,而是一个复制之前状态,然后加上动作改变的部份,产生的一个新的对象,它这样设计是有原因的。

Redux的store设计,并不是原本Flux架构中的store,而是ReduceStore,这个ReduceStore是一个在Flux中的store进化版本,在说明中它有一个叫作reduce的方法,说明如下:

reduce(state: T, action: Object): T 归纳(Reduces)目前的state(状态)与一个action(动作)到新的store中的state(状态)。所有的子类都需要实作这个方法。这个方法必须是纯粹而是无副作用。

那为何要用这个进化的ReduceStore?它最后有说明一段:

不需要发送更动事件注意所有继承自ReduceStore的store,不需要手动发送在reduce()中的更动事件...state(状态)会自动地比对在每个dispatch(发送)之前与之后,与自动地作发送更动事件...

ReduceStore的设计与Redux最一开始的版本差不多是同时间发布的,在开发者之间彼此有交流。Redux的store运用了类似于ReduceStore的设计,所以要更动Redux中的store,需要透过reducer,这是为了简化原本在Flux数据流的实作流程。

reducer在Redux中扮演了十分重要的关键角色,它是一种对store中所存放的状态,要如何因应不同的动作而进行刷新的函数,而store也是由reducer所创建,例如像下面的代码:

// @Reducer
//
// action payload = action.text
// 使用纯粹函数的数组unshift,不能有副作用
// state(状态)一开始的值是空数组`state=[]`
function todoApp(state = [], action) {
  switch (action.type) {
    case "ADD_ITEM":
      return [action.text, ...state]
    default:
      return state
  }
}

// @Store
//
// 由reducer创建store
const store = createStore(todoApp)

针对应用中不同功能的状态,可以分别写出不同的reducer,Redux中提供了combineReducers函数可以合并多个reducer,例如以下的代码:

function todos(state = [], action) {
  switch (action.type) {
    case "ADD_TODO":
      return state.concat([ action.text ])
    default:
      return state
  }
}

function counter(state = 0, action) {
  switch (action.type) {
    case "INCREMENT":
      return state + 1
    case "DECREMENT":
      return state - 1
    default:
      return state
  }
}

// rootReducer是个组合过的函数,
// 这里用的是对象属性初始设置简写法,
// combineReducers传参是一个对象
const rootReducer = combineReducers({
  todos,
  counter
})

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/81350.html

相关文章

  • Redux 入门

    摘要:系列文章入门本文进阶番外篇状态管理,第一次听到这个词要追溯到去年年底。只读的唯一改变的方法就是触发,是一个用于描述已发生事件的普通对象。没有特殊情况没有副作用,没有请求没有变量修改,只进行单纯执行计算。 系列文章: Redux 入门(本文) Redux 进阶 番外篇: Vuex — The core of Vue application 状态管理,第一次听到这个词要追溯到去年年...

    shusen 评论0 收藏0
  • 解密Redux: 从源码开始

    摘要:接下来笔者就从源码中探寻是如何实现的。其实很简单,可以简单理解为一个约束了特定规则并且包括了一些特殊概念的的发布订阅器。新旧中存在的任何都将收到先前的状态。这有效地使用来自旧状态树的任何相关数据填充新状态树。 Redux是当今比较流行的状态管理库,它不依赖于任何的框架,并且配合着react-redux的使用,Redux在很多公司的React项目中起到了举足轻重的作用。接下来笔者就从源码...

    remcarpediem 评论0 收藏0
  • Redux 入门

    摘要:只要是同样的输入,必定得到同样的输出。纯函数是函数式编程的概念,必须遵守以下一些约束。中的概念执行的动作,包括动作所需要的数据,改变数据的唯一来源,一般是通过将传到。只是描述了有事情发生了这一事实,并没有指明应用如何更新。 1.什么是Redux 管理Web应用全局状态的框架。 单页面应用,顾名思义,和传统项目的最明显区别就是项目只有一个页面,页面有一个根元素,我们写的每一个页面是一个大...

    miracledan 评论0 收藏0
  • React-redux基础

    摘要:简介创建的函数,返回一个对象,包含等方法合并多个中间件处理,在实际的前调用一系列中间件,类似于绑定和函数式编程中常见的方法,介绍官方提供的绑定库。 前言 在学习了React之后, 紧跟着而来的就是Redux了~ 在系统性的学习一个东西的时候, 了解其背景、设计以及解决了什么问题都是非常必要的。接下来记录的是, 我个人在学习Redux时的一些杂七杂八~ Redux是什么 通俗理解 h...

    jsyzchen 评论0 收藏0
  • Redux技术架构简介

    摘要:是一个程序架构,源于提出的一种架构,然而,它不仅可以应用于,还可以应用于其他任何框架中。有以下职责维持应用的提供方法获取提供方法更新通过注册监听器通过返回的函数注销监听器。同时,的返回值实际上是一个函数可以解除监听。 Redux是一个程序架构,源于Flux(Facebook提出的一种架构),然而,它不仅可以应用于React,还可以应用于其他任何框架中。值得一提的是,Redux的源代码很...

    weizx 评论0 收藏0

发表评论

0条评论

最新活动
阅读需要支付1元查看
<