javascript 如果useEffect没有第二个参数,或者第二个参数为null或undefined,会发生什么情况?

cunj1qz1  于 2022-12-10  发布在  Java
关注(0)|答案(2)|浏览(415)

我只是想知道,如果我们将第二个参数作为nullundefined来传递,useEffect将如何表现。它会在每个周期都呈现吗?还是只呈现一次?任何线索都将不胜感激。

qhhrdooz

qhhrdooz1#

如果你创建了一个useEffect,没有第二个参数,或者有一个等于undefinednull的参数,那么回调函数会在每个渲染器上执行。如果你显式输入了undefinednull作为第二个参数,并且你的编辑器中有Eslint,你会收到这样的警告:

React Hook useEffect was passed a dependency list that is not an array literal. This means we can't statically verify whether you've passed the correct dependencies. (react-hooks/exhaustive-deps)

在下面这种情况下,您不会对应用程序造成任何损害,在这种情况下,您不会在回调中修改state,它只会在每次呈现时记录“Hello Word”。

export default function App() {
  const [state, setState]= useState(true);
  useEffect(() => {
    console.log("Hello Word");
  });
  return (
    <div>
      <button onClick = {()=>setState(!state)}>Toggle State</button>
    </div>
  );
}

在回调函数中修改state的情况下,会导致渲染的无限循环。这是因为状态改变会触发渲染,并且回调函数会在每个渲染上执行。

export default function App() {
  const [state, setState]= useState(true);
  useEffect(() => {
   setState(!state);
  });
  return (
    <div>
      <button onClick = {()=>setState(!state)}>Toggle State</button>
    </div>
  );
}

为了涵盖所有用例,第二个参数为空的dependencies数组,其中回调只在第一次渲染时执行:

export default function App() {
  const [state, setState]= useState(true);
  useEffect(() => {
   setState(!state);
  },[]);
  return (
    <div>
      <button onClick = {()=>setState(!state)}>Toggle State</button>
    </div>
  );
}

最后,在第一次渲染时以及每次dependencies数组中的某个state发生更改时调用回调的函数:

export default function App() {
  const [state, setState]= useState(true);
  useEffect(() => {
   console.log("Hello Word");
   // setState(!state); if you mutate state here, it will cause an infinite loop of renders
  },[state]);
  return (
    <div>
      <button onClick = {()=>setState(!state)}>Toggle State</button>
    </div>
  );
}
yvt65v4c

yvt65v4c2#

如果deps未定义或为空,它将重新渲染每个圆。
在React源代码中,当第二个参数未定义时,deps将为null,updateEffectImpl将始终执行pushEffect,并渲染每个圆:

function updateEffectImpl(fiberFlags, hookFlags, create, deps): void {
  const nextDeps = deps === undefined ? null : deps;

  if (currentHook !== null) {
    // .eg
  }

  // always execute
  hook.memoizedState = pushEffect(
    HookHasEffect | hookFlags,
    create,
    destroy,
    nextDeps,
  );
}

相关问题