在React中使用派生状态

来自菜鸟教程
跳转至:导航、​搜索

React v16.3 引入了一些有趣的新特性,比如 getDerivedStateFromProps 方法。 在这篇文章中,我们将探讨如何使用它。

React v16.3 中,引入了 getDerivedStateFromProps 静态生命周期方法来替代 componentWillReceiveProps。 将组件迁移到这种新方法很重要,因为 componentWillReceiveProps 很快将在即将发布的 React 版本中被弃用。

就像 componentWillReceiveProps 一样,只要组件接收到新的 props,就会调用 getDerivedStateFromProps

组件WillReceiveProps

这是旧方法的示例:

// For example purposes only, this is now deprecated

class List extends React.Component {
  componentWillReceiveProps(nextProps) {
    if (nextProps.selected !== this.props.selected) {
      this.setState({ selected: nextProps.selected });
      this.selectNew();
    }
  }

  // ...
}

如您所见,componentWillReceiveProps 通常用于更新组件的状态。 它也可能有副作用,例如调用 this.selectNew()

getDerivedStateFromProps

新方法的工作方式有点不同:

class List extends React.Component {
  static getDerivedStateFromProps(props, state) {
    if (props.selected !== state.selected) {
      return {
        selected: props.selected,
      };
    }

    // Return null if the state hasn't changed
    return null;
  }

  // ...
}

与第一个示例中那样调用 setState 不同,getDerivedStateFromProps 只是返回一个包含更新状态的对象。 请注意,该函数没有副作用; 这是故意的。

getDerivedStateFromProps 可能会被多次调用以进行一次更新,因此避免任何副作用很重要。 相反,您应该使用 componentDidUpdate,它只在组件更新后执行一次。

这是我们的最终代码:

class List extends React.Component {
  static getDerivedStateFromProps(props, state) {
    if (props.selected !== state.selected) {
      return {
        selected: props.selected,
      };
    }

    // Return null if the state hasn't changed
    return null;
  }

  componentDidUpdate(prevProps, prevState) {
    if (this.props.selected !== prevProps.selected) {
      this.selectNew();
    }
  }

  // ...
}

包起来

getDerivedStateFromProps 通过提供一个函数来改进旧方法,该函数的唯一目的是根据 prop 更改更新状态,没有任何副作用。 这使得组件作为一个整体更容易推理。

然而,派生状态给组件增加了一些复杂性,而且通常是完全没有必要的。 查看帖子 你可能不需要派生状态 以获取替代方案。