【问题标题】:Updating state repeatedly - ReactJs反复更新状态 - ReactJs
【发布时间】:2020-11-03 03:49:28
【问题描述】:

您好我有一个父组件,有两个子组件,如下所示,Child1 具有可拖动的 div 元素,它在拖动时为父组件提供值,然后我必须将其传递给 Child2 并使用,但在 Child2 中使用它之前我必须进行几十次计算。

const Parent = () => {
  const [dragValue, setDragValue] = useState(0);
  const dragHanlder = (dragVal) => {
     setDragValue(dragVal);
  };
  return (
        <Child1 mouseDrag={dragHanlder} />
        <Child2 dragValue={dragValue}/>
  );
}

class Child2 extends React.Component {
   state = {
     afterCalculationsVal: 0
   };
   componentDidUpdate = () => {
      const { dragValue } = this.props;
      const someFinalval = val //this val takes dragValue applies checks, calculations and conditions and finally gives out some value
      this.setState({afterCalculationsVal: someFinalval });
   };

   render() {
      const { afterCalculationsVal } = this.state;
      return (
         <Child3 afterCalculationsVal={afterCalculationsVal} >
      );
   }
}

问题是我遇到了达到最大深度的问题,因为我正在设置连续拖动的状态。有什么办法可以克服这个。我不能直接使用 Child2 中 props 中的 'dragValue',必须计算 props 值,然后我必须设置 state。

【问题讨论】:

  • 一般来说,当您想根据传入的 props 计算值时,您希望在 render() 方法中将其作为“计算属性”而不是设置为状态。在这种情况下,您基本上创建了一个无限循环。每次组件更新时都会调用 componentDidUpdate,其中包括设置状态。由于在设置状态之前您没有在 componentDidUpdate 中进行任何检查,因此您会超出此最大深度,因为 setState 正在使组件立即再次调用 componentDidUpdate。然后再一次。又一次
  • "您可以在 componentDidUpdate() 中立即调用 setState(),但请注意,它必须像上面的示例一样包装在条件中,否则会导致无限循环"reactjs.org/docs/react-component.html跨度>
  • 问题是由于 componentDidUpdate 中的 setState 导致无限循环。除此之外,您可以在拖动处理程序上使用去抖动,这将导致 child2 的重新渲染次数减少
  • 已经给出了两个答案。你能给他们反馈吗?他们有没有回答你的问题?如果你问一个问题,人们努力回答,你保持沉默,没有投票,没有接受标记,这很不好......

标签: javascript reactjs react-props


【解决方案1】:

问题是当组件更新时它会进入 componentDidUpdate 然后设置状态导致另一个更新。设置 if 条件检查拖动值应该可以解决您的问题。

componentDidUpdate = (prevProps, prevState) => {
    const { dragValue } = this.props;
    if(prevState.dragValue !== prevState.dragValue){
      // Will only re-render when dragValue changes
      const someFinalval = val 
      this.setState({afterCalculationsVal: someFinalval });
    }
  };

【讨论】:

    【解决方案2】:

    永远不要在 componentdidupdate 中使用 this.setState 而不检查你改变的值是否真的改变了。事实上这会触发一个无限循环

    componentDidUpdate = () => {
          const { dragValue } = this.props;
          const someFinalval = val //this val takes dragValue applies checks, calculations and conditions and finally gives out some value
          if(/** your check *//)
          this.setState({afterCalculationsVal: someFinalval });
       };
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-12-30
      • 1970-01-01
      • 1970-01-01
      • 2018-07-25
      • 2014-09-20
      • 1970-01-01
      相关资源
      最近更新 更多