为什么在redux中更改状态和操作是有益的?

为什么在redux中更改状态和操作是有益的?,redux,Redux,发件人: 状态为只读。改变状态的唯一方法是发出一个动作,一个描述发生了什么的对象。这确保了视图和网络回调都不会直接写入状态。相反,它们表达了改变国家的意图。因为所有的变化都是集中的,并且以严格的顺序一个接一个地发生,所以没有微妙的种族条件需要注意。由于操作只是普通对象,因此可以对其进行记录、序列化、存储,并在以后出于调试或测试目的进行回放 我由此产生了两个问题 redux是如何严格按照顺序执行更改的?如果我同步改变状态,那么我不明白为什么这会成为一个问题。如果我想按顺序更改异步事件1和异步事件2

发件人:

状态为只读。改变状态的唯一方法是发出一个动作,一个描述发生了什么的对象。这确保了视图和网络回调都不会直接写入状态。相反,它们表达了改变国家的意图。因为所有的变化都是集中的,并且以严格的顺序一个接一个地发生,所以没有微妙的种族条件需要注意。由于操作只是普通对象,因此可以对其进行记录、序列化、存储,并在以后出于调试或测试目的进行回放

我由此产生了两个问题

  • redux是如何严格按照顺序执行更改的?如果我同步改变状态,那么我不明白为什么这会成为一个问题。如果我想按顺序更改异步事件1和异步事件2之后的状态,那么无论是否使用redux,我都不需要执行类似使用回调或承诺之类的操作,以确保状态按预期的顺序更改吗
  • 为什么记录操作更容易?如果我没有使用redux,我能不能只将我所做的每一个状态更改都记录下来,以便于调试和测试?我只是通过学习redux节省了每次状态更改时编写console.log的时间吗

  • 回答您的问题:

  • redux的执行是同步的,因此当您分派一个操作时,您正在redux存储上执行一个方法,该方法调用reducer来计算新状态。redux中不存在“异步操作”的概念,这就是为什么有大量解决方案支持它们:redux thunk、redux saga、redux observable等等。所有“异步操作”库最终都必须同步执行分派函数以更改redux状态

  • 在编写良好的redux应用程序中,对redux存储中包含的任何状态的更改只能由从应用程序中具有调度功能的某处调度的操作引起。这使您能够完全控制和了解状态更改发生的位置和方式。这就是redux的主要卖点:“可预测的状态容器”。您当然可以将您的本地状态存储在某个全局变量中,并手动对其进行变异,但随后您必须在该状态变量上使用类似(实际上已弃用,没有替换)的内容来监视对其的更改


  • 1.关键是,您没有异步状态更改。您可能会有由异步事件触发的状态更改,这是不同的。2.“…序列化、存储并稍后重播”-您是否也要为每个状态更改编写所有这些内容?@jonrsharpe我想我现在明白第二点了。所以基本上,如果我的状态分散在我的应用程序中,那么每次更改时都很难将我的状态存储在数据库中。redux store本质上是一个JS对象,包含您的状态和观察状态的函数?关于第1点,我想我还不清楚redux同步的好处是什么?因为状态更改可能总是同步的,除非您使用异步函数来像React的setState那样进行更改。我还没有使用redux中间件,但是你是说,如果异步事件1比正常情况下需要更长的时间,那么异步事件2会首先发生,那么状态变化可能无法预测,那么他们会以某种方式绕过这种情况吗?不管怎样,为什么我不能使用回调或承诺来强制执行事件的顺序?[1/4]您的问题1问为什么状态更改一定会按严格的顺序发生,我的回答是“redux就是这样工作的”。为了解决您提出的新问题,是的,当您使用“异步操作”时,状态更改确实会更不可预测因为现在,除了要调度的操作之外,时间也是一个因素。例如,按该顺序发出的AJAX请求1和2(对于自动完成框)可能会以相反的顺序返回,并可能会扰乱您的状态。[2/4]要回答您的问题,为什么回调和承诺可能无法帮助您执行命令,让我们看看redux thunk中间件如何帮助异步操作。对于每个“触发器”(例如,数据提取),中间件都会发送一个事件,通知redux状态切换到“挂起”状态(例如,这样您可以显示加载微调器),同时中间件执行异步活动(例如,实际发送提取请求)。[3/4]异步活动完成时,中间件发送一个操作,告诉redux状态活动的成功或失败(以便可以相应地更新UI)。考虑到这样一个中间件的工作方式,每个异步“触发器”对应于单独的操作,并且完全不知道彼此。可以使用更高级的中间件(如redux-observable)协调多个异步操作。如果为了响应单个触发器,需要先执行异步活动1,然后再执行异步活动2,则只需将它们放在一个thunk中即可确保它们按该顺序执行(如果使用原始
    承诺
    s,则适当使用
    。然后
    链接;如果在
    异步
    函数中,则使用连续的
    等待
    语句).我的观点是,如果触发器1导致异步活动2,触发器2导致异步活动2,那么即使触发器1发生在触发器2之前,也很难协调两个异步活动的完成顺序,除非您达到类似于
    redux observable
    的目标。