反应:在设置状态时重新渲染-挂钩与this.setState

时间:2019-03-27 09:34:46

标签: javascript reactjs react-hooks

类组件

在React类组件中,我们被告知setState 总是会导致重新渲染,而不管状态是否实际更改为新值。实际上,当状态更新为以前的相同值时,组件重新渲染。

Docs (setState API Reference)

  

setState()将始终导致重新渲染,除非   shouldComponentUpdate()返回false。


挂钩(功能组件)

但是,使用钩子,文档将更新状态指定为与先前状态相同的值,不会会导致(子组件的)重新渲染:

Docs (useState API Reference)

  

退出状态更新

     

如果将状态挂钩更新为与当前状态相同的值,   React将纾困而不会渲染子代或发射效果。   (React使用Object.is比较算法。)


密切相关的问题

  1. 即使新的this.setState值与先前的值相同,类组件中的state总是引起重新渲染是否正确?
  2. 是否正确,在带有钩子的功能组件中,setState中的useState仅在state值与先前值不同时才导致重新渲染价值?
  3. 正在类组件的state方法内用this.setState设置render,与在函数主体内设置state相同带有钩子的功能组件
  4. 以下正确吗?
    • 类组件中,如果我们在state方法中设置render,则会发生无限循环。这是因为 class组件不在乎新的state与先前的state是相同的。它只是不断在每个this.setState上重新渲染。
    • 但是在带有钩子的功能组件中,在功能体内设置state(重新渲染时运行,类似于类组件中的render方法) 不成问题,因为功能组件在发现state与上一个state

2 个答案:

答案 0 :(得分:5)

  

在类组件中this.setState总是会导致   重新渲染,即使新的状态值与以前的状态值相同?

如果您在setState内设置了一个有效值(除了返回null之外),则除非组件是PureComponent或实现了shouldComponentUpdate,否则类组件中的react总是会触发re-render

  

在带有钩子的函数组件中,setState是否正确?   useState仅在状态值与以下值不同时才导致重新渲染   以前的值?

对于使用useState挂钩的功能组件,setter(如果以相同状态调用)将不会触发重新渲染。但是,在偶尔的情况下,如果立即调用setter,则会导致两个渲染而不是一个渲染

  

正在使用this.setState设置状态吗?   类组件,与功能体内的设置状态相同   带有钩子的功能组件?

技术上可以,直接在render方法中设置状态将导致函数在类组件导致无限循环的情况下触发重新渲染,如果状态值不同,则对于功能组件而言就是这种情况。无论如何,它仍然会引起问题,因为由于功能组件直接调用状态更新,其他任何状态更新都将被还原

  

在类组件中,如果我们在render方法中设置状态为无穷大   循环将发生。这是因为类组件不在乎   新状态与先前状态相同。它保持   在每个this.setState上重新渲染。

是的,因此建议不要在渲染中直接调用setState

  

但是,在具有挂钩的功能组件中,请在   函数体(在重新渲染时运行,类似于render方法   在类组件中)不会有问题,因为该函数   组件看到状态为   与以前的状态相同。

不是100%正确,因为您可以使用前一个值触发状态更新,从而使前一个值和当前值不同。例如

setCount(count => count + 1);

在这种情况下,您的组件仍然会陷入无限循环

答案 1 :(得分:0)

这不是OP的直接答案,但与OP和Hooks的新手并为他们的副作用和渲染时间而苦苦挣扎的某些人相关,可能对他们有所帮助。

由于尚未在此处提及:在功能组件中,而不是使用前面提到的(请参见接受的答案的注释)ShouldComponentUpdate()函数(仅适用于基于类的组件),您可以使用{ {1}}钩。有了它,您可以告诉您的组件何时以及在哪种情况下产生副作用,例如当某些依赖关系改变时。

在React文档的此示例中,仅当useEffect()更改时,该函数才会执行。

props.source

React docs: useEffect()