【问题标题】:reactjs : ShouldComponentUpdate for statesreactjs : 状态的 ShouldComponentUpdate
【发布时间】:2016-10-07 23:13:03
【问题描述】:

如何将shouldComponentUpdate 用于状态?

我可以检查:

shouldComponentUpdate(nextProps, nextState) {
  return this.state.value != nextState.value;
}

但它对状态没有任何意义。因为如果我改变状态(this.setState({value: 'newValue'})this.state 将等于nextState

例如onClick事件:

handleClick() {
  this.setState({value: 'newValue'});
}

【问题讨论】:

  • 组件应该在状态改变时简单地重新渲染,我认为shouldComponentUpdate 主要用于道具,而不是状态。从specs 可以看出,您可以决定新状态是否需要更新组件,例如,您可能有不需要更新当前状态的逻辑,但您无法将其与之前的状态进行比较可以带道具
  • @Icepickle,就我而言,我想比较状态,因为我的组件没有得到props,而是父组件重新渲染它。
  • 比较状态并决定你想在你实际改变它的地方更新它

标签: reactjs


【解决方案1】:

shouldComponentUpdate(nextProps, nextState) 方法适用于 props 和 state。在您的示例中,在 onClick 事件之后,React 会触发以下方法。

shouldComponentUpdate(nextProps, nextState) {
  return this.state.value != nextState.value;
}

这里的关键是,在上述方法中,this.state.value 的值等于 setState() 调用之前的值。这要归功于在 React 中:

setState() 不会立即改变 this.state 而是创建一个 等待状态转换。
React 文档:https://facebook.github.io/react/docs/component-api.html#setstate

看看这个演示:http://codepen.io/PiotrBerebecki/pen/YGZgom(下面的完整代码)

React 保持状态,每次点击按钮的计数,并保存随机选择的value(true 或 false)。然而,由于shouldComponentUpdate 方法,只有当previous value 不等于即将到来的/新的value 时,才会重新渲染组件。这就是为什么显示的点击计数有时会跳过呈现其当前状态的原因。您可以注释掉整个 shouldComponentUpdate 方法,以便在每次点击时重新渲染。

class App extends React.Component {
  constructor() {
    super();
    this.state = {
      value: true,
      countOfClicks: 0
    };
    this.pickRandom = this.pickRandom.bind(this);
  }

  pickRandom() {
    this.setState({
      value: Math.random() > 0.5, // randomly picks true or false
      countOfClicks: this.state.countOfClicks + 1
    });
  }

  // comment out the below to re-render on every click
  shouldComponentUpdate(nextProps, nextState) {
    return this.state.value != nextState.value;
  }

  render() {
    return (
      <div>
        shouldComponentUpdate demo 
        <p><b>{this.state.value.toString()}</b></p>
        <p>Count of clicks: <b>{this.state.countOfClicks}</b></p>
        <button onClick={this.pickRandom}>
          Click to randomly select: true or false
        </button>
      </div>
    );
  }
}

ReactDOM.render(
  <App />,
  document.getElementById('app')
);

【讨论】:

  • 谢谢。这很奇怪,因为我在constructor 中设置了'value:'''。在onClick 事件之后,我在shouldComponentUpdate 中得到this.state.valuenewValue。但我认为应该是this.state.value = '', nextState.value = 'newValue'
  • 在这里查看控制台输出:codepen.io/PiotrBerebecki/pen/LRdppQ。初始值为0,因此当您单击按钮时,this.state.countOfClicks0nextState.countOfClicks1。您还可以看到 shouldComponentUpdate this.state.countOfClicks 内部总是落后于屏幕上实际呈现的内容。有意义吗?
  • 是的,我测试了你的例子。有用。但在我的真实项目中this.state 等于nextState。那很奇怪。继续寻找。也许我做错了什么。谢谢。
  • 好的,谢谢。我在调用setState 之前更改了状态。 let state = this.state; state.value = 'newValue'; this.setState(state);
  • 用下面的方式更新你的状态:this.setState({ value: 'newValue' }); 就是这样。这是一个简单的演示:codepen.io/PiotrBerebecki/pen/GjdgJK
猜你喜欢
  • 2023-03-04
  • 2017-11-15
  • 1970-01-01
  • 2015-11-14
  • 2016-02-19
  • 2018-01-29
  • 2016-04-03
  • 2019-06-30
  • 1970-01-01
相关资源
最近更新 更多