React hook useEffect永远持续运行/无限循环

时间:2018-11-10 20:40:37

标签: javascript reactjs react-hooks

我正在尝试新的React HooksuseEffect API,它似乎可以无限循环地永远运行!我只希望useEffect中的回调运行一次。这是我的代码供参考:

单击“运行代码段”以查看“ Run useEffect”字符串正在无限打印到控制台。

function Counter() {
  const [count, setCount] = React.useState(0);

  React.useEffect(() => {
    console.log('Run useEffect');
    setCount(100);
  });

  return (
    <div>
      <p>Count: {count}</p>
    </div>
  );
}

ReactDOM.render(<Counter />, document.querySelector('#app'));
<script src="https://unpkg.com/react@16.7.0-alpha.0/umd/react.development.js"></script>
<script src="https://unpkg.com/react-dom@16.7.0-alpha.0/umd/react-dom.development.js"></script>

<div id="app"></div>

1 个答案:

答案 0 :(得分:11)

之所以会发生这种情况,是因为useEffect在每次渲染之后都会触发,这是在无状态功能组件的情况下Counter()函数的调用。当您在setX中执行从useState返回的useEffect调用时,React将再次渲染该组件,并且useEffect再次运行。这会导致无限循环:

Counter()useEffect()setCount()Counter()useEffect()→...(循环)

要使您的useEffect仅运行一次,请传递一个空数组[]作为第二个参数,如下面的修订代码段所示。

第二个参数的目的是告诉React数组参数中的任何值何时更改:

useEffect(() => {
  setCount(100);
}, [count]); // Only re-run the effect if count changes

您可以将任意数量的值传递给数组,并且useEffect仅在其中任何一个值更改时才会运行。通过传入一个空数组,我们告诉React不要跟踪任何更改,只能运行一次,有效地模拟componentDidMount

function Counter() {
  const [count, setCount] = React.useState(0);

  React.useEffect(() => {
    console.log('Run useEffect');
    setCount(100);
  }, []);

  return (
    <div>
      <p>Count: {count}</p>
    </div>
  );
}

ReactDOM.render(<Counter />, document.querySelector('#app'));
<script src="https://unpkg.com/react@16.7.0-alpha.0/umd/react.development.js"></script>
<script src="https://unpkg.com/react-dom@16.7.0-alpha.0/umd/react-dom.development.js"></script>

<div id="app"></div>

详细了解useEffect