Warum wird useEffect ausgelöst, wenn ich eine Funktion aus Requisiten verwende (die Funktion hat sich nicht geändert)?
P粉662802882
P粉662802882 2023-09-12 22:40:30
0
1
433

Die Hauptkomponente ist der Aufruf des Modals/Dialogs.

[...]
  const closeDialog = () => setIsOpenDialog(false);
  return (
      <MyDialog
        isOpen={isOpenDialog}
        onClose={closeDialog}
      />
  );

MyDialog-Code lautet:

[...]
  useEffect(() => {
    console.log('This removes dialog states (data)!')
  }, [onClose]);

export default function MyDialog({
  isOpen,
  onClose,
}) {
    return (
    <Dialog
      isOpen={isOpen}
      onClose={onClose}
      dialogTitle="Add/Edit"
      onClickCancel={onClose}
    >
    [...]
    </Dialog>
);
}

Wenn ich auf „Abbrechen“ klicke und anrufe onClose 时,我可以看到 useEffect触发。请问这是什么原因呢?我的理解是不应该,因为 onClose 函数对象(来自 props) ändert sich nichts.

P粉662802882
P粉662802882

Antworte allen(1)
P粉165823783

当依赖数组中的任何依赖项发生更改时,React 中的 useEffect 挂钩就会运行。在您的情况下,useEffect 依赖于onClose 属性。因此,每次 onClose 属性更改时都会运行。

但是,即使代码中的 onClose 函数未发生更改,由于 JavaScript 处理函数标识的方式,useEffect 可能仍会运行。在 JavaScript 中,每次定义函数时,它都是一个新实例,即使它执行完全相同的操作。

因此,就您而言,每次组件重新渲染时,您都将 closeDialog 定义为渲染函数中的新函数。这意味着,从 React 的角度来看,onClose 每次都是一个新函数,它会触发 useEffect

要解决此问题,您可以使用 useCallback 挂钩来确保您的 closeDialog 函数在渲染之间具有稳定的标识,除非其依赖项发生变化:

const closeDialog = React.useCallback(() => setIsOpenDialog(false), []);

在上面的示例中,useCallback 返回函数的记忆版本,该版本仅在依赖项之一发生更改时才会更改。在这种情况下,依赖项数组为空 ([]),这意味着 closeDialog 函数的标识在重新渲染时将保持稳定。

Beliebte Tutorials
Mehr>
Neueste Downloads
Mehr>
Web-Effekte
Quellcode der Website
Website-Materialien
Frontend-Vorlage
Über uns Haftungsausschluss Sitemap
Chinesische PHP-Website:Online-PHP-Schulung für das Gemeinwohl,Helfen Sie PHP-Lernenden, sich schnell weiterzuentwickeln!