同时调用this.setState函数

时间:2018-05-17 12:58:14

标签: javascript reactjs state

我遇到一个问题,即各种子组件同时调用setState

以下是一些过于简单化的代码:

var Content = React.createClass({
  updateElements: function(element) {
    elements = [].concat(this.state.elements)
    elements.push(element)
    this.setState({ elements })
  }

  render: function() {
    elements = ["a", "b"];

    return (
      <div>
        <Element updateElements={this.updateElements} data={elements[0]} />
        <Element updateElements={this.updateElements} data={elements[1]} />
      </div>
    );
  }
});

var Element = React.createClass({
  componentDidMount: function() {
     this.props.updateElements(this.props.data)
  }

  render: function() {
    return (
      <div>
         {this.props.data}
      </div>
    );
  }
});

ReactDOM.render(
  <Content />,
  document.getElementById('container')
);

我可以以某种方式等待先前的状态设置再次更新吗?

2 个答案:

答案 0 :(得分:1)

我不完全确定,但这应该有效。如果你像这样做setState

this.setState((prevState, props) => {
  return {elements: [...prevState.elements, element]};
});

它不会同步但它应该保持元素而不会覆盖它(因为同时更新),因为它将从prevState获取。

答案 1 :(得分:1)

根据setState documentation

  

这种形式的setState()也是异步的,并且是多次调用   在同一周期内可以一起批量生产

这意味着假设您有2个子元素调用以下父方法:

  doSomething1(amount){
    this.setState({
      sum1: this.state.sum1 + amount
    }, () => {
      console.warn(this.state.sum1); // 1
    })
  }

两者都将记录1,因为后续调用将覆盖同一周期中先前调用的值,因此数量将仅增加一次。

相反,您应该使用更新程序功能形式:

  doSomething2(amount) {
    this.setState((prevState) => {
      return { sum2: prevState.sum2 + amount };
    }, () => {
      console.warn(this.state.sum2); // 2
    });
  }

Live example

如果您的问题取决于州的先前价值,这可以解决您的问题。