我知道React可能会异步和批量地执行状态更新,以进行性能优化。因此,在调用setstate
之后,您永远不能相信会更新状态。但是,您是否信任React按照调用setstate
时的顺序更新状态
class Container extends React.Component {
constructor(props) {
super(props);
this.state = { a: false, b: false };
}
render() {
return <Button onClick={this.handleClick}/>
}
handleClick = () => {
this.setState({ a: true });
this.setState({ b: true });
}
}
class SuperContainer extends React.Component {
constructor(props) {
super(props);
this.state = { a: false };
}
render() {
return <Container setParentState={this.setState.bind(this)}/>
}
}
class Container extends React.Component {
constructor(props) {
super(props);
this.state = { b: false };
}
render() {
return <Button onClick={this.handleClick}/>
}
handleClick = () => {
this.props.setParentState({ a: true });
this.setState({ b: true });
}
}
任何有文档支持的答案都是非常感谢的。
我在React工作。
TLDR:
但是您是否可以信任React以调用setState时所需的相同顺序更新状态
目前(React16及更早版本),默认情况下只批处理React事件处理程序中的更新。有一个不稳定的API来强制在事件处理程序之外进行批处理,以满足极少数情况下的需要。
在以后的版本中(可能是React17和更高版本),React将默认批处理所有更新,因此您不必考虑这个问题。和往常一样,我们将在React博客和发行说明中宣布有关这方面的任何变化。
理解这一点的关键是,无论您在React事件处理程序中调用多少个组件中的setstate()
调用多少个组件,它们都只能在事件结束时生成一个重新呈现。这对于大型应用程序中的良好性能至关重要,因为如果子
和父
在处理click事件时都调用setstate()
,您就不想重新呈现子
两次。
当我们在批处理结束时重新呈现UI时,this.state
对象会更新。因此,如果需要根据以前的状态更新状态(例如增加计数器),则应该使用函数化的setstate(fn)
版本来提供以前的状态,而不是从this.state
中读取。如果你对此的原因感到好奇,我在这篇评论中对此进行了深入的解释。
在您的示例中,我们不会看到“中间状态”,因为我们位于启用批处理的React事件处理程序中(因为React“知道”我们何时退出该事件)。
但是,在React16和早期版本中,默认情况下在React事件处理程序之外都没有批处理。因此,如果在您的示例中我们有一个AJAX响应处理程序而不是handleClick
,那么每个setstate()
将在发生时立即处理。在本例中,是的,您将看到一个中间状态:
promise.then(() => {
// We're not in an event handler, so these are flushed separately.
this.setState({a: true}); // Re-renders with {a: true, b: false }
this.setState({b: true}); // Re-renders with {a: true, b: true }
this.props.setParentState(); // Re-renders the parent
});
promise.then(() => {
// Forces batching
ReactDOM.unstable_batchedUpdates(() => {
this.setState({a: true}); // Doesn't re-render yet
this.setState({b: true}); // Doesn't re-render yet
this.props.setParentState(); // Doesn't re-render yet
});
// When we exit unstable_batchedUpdates, re-renders once
});
在内部,React事件处理程序都包装在unstable_batchedUpdates
中,这就是为什么它们在默认情况下是批处理的。请注意,在unstable_batchedUpdates
中包装更新两次没有效果。当我们退出最外层的unstable_batchedUpdates
调用时,更新将被刷新。
该API是“不稳定的”,因为我们将在默认情况下启用批处理时删除它。但是,我们不会在次要版本中删除它,所以如果在某些情况下需要在React事件处理程序之外强制批处理,您可以安全地依赖它,直到React17。
总而言之,这是一个令人困惑的主题,因为默认情况下React只在事件处理程序中进行批处理。这将在未来的版本中改变,并且行为将更加直接。但解决办法不是减少批处理,而是在默认情况下增加批处理。这就是我们要做的。
问题内容: 我知道React可以异步并批量执行状态更新以优化性能。因此,在调用之后,您将永远无法相信要更新的状态。但是你可以信任的反应 更新相同的顺序状态被称为对 相同的组件? 不同的组件? 考虑在以下示例中单击按钮: 1. 在以下情况下,是否有可能 a为假而b为真 : 2. 在以下情况下,是否有可能 a为假而b为真 : 请记住,这些是我用例的极端简化。我意识到我可以以不同的方式进行操作,例如,在
问题内容: hibernate状态是否保留LinkedHashSet的顺序?如果是,则如何?如果这取决于数据库的类型,那么我想对PostgreSQL有所了解。 背景: 我知道LinkedHashSet的用途是什么,我之所以问这个原因是因为我正在将执行的某些函数的名称记录到与某些“ functionName”表具有多对多关系的“ logError”表中。我需要这些函数保持与执行它们时相同的顺序,因此
问题内容: Java的foreach循环是否从第一个对象开始,并且以线性方式工作到结束?例如 是否总是先处理字符串“ Zoe”,然后处理“ Bob”等?没有排序发生?我已经对它进行了测试,但没有找到任何东西,但是我需要保证,在文档中找不到任何东西。 问题答案: 是。顺序不变。这适用于Java类集合框架的所有类型的集合,这些集合实现由for循环使用的迭代器接口。如果要对数组进行排序,则可以使用Arr
我试图将“加载”的状态从true更改为false,但当我调用一个函数并在该函数中设置“this.setState({loading:false})”时,加载状态仍然保持true。 在下面的代码中,当按钮按钮函数被调用时,它将“加载”状态设置为真,但当用户成功登录“加载”状态时,应该变为假,这样我的渲染按钮函数将重新渲染,旋转器可以隐藏自己并显示按钮。 为什么LoginSAccess函数中的“加载”
所以我有这个: 只是一个数组的数字例如然而没有给出正确的总数,但?我甚至放了一个超时延迟,看看这是否解决了问题。任何明显的还是我应该发布更多的代码?
问题内容: 我特别想知道PostgreSQL。给出以下人为的示例: 从外部查询返回的名称是否保证与内部查询的顺序相同? 问题答案: 不,在外部查询中按以下顺序排序: 内部(子)查询返回结果集。如果按此顺序进行排序,则保证从内部(子)查询传递到外部查询的中间结果集将按照您指定的方式进行排序,但是在外部查询中不对结果进行排序通过处理内部查询结果集生成的结果集,不能保证以任何方式进行排序。