javascript - 我已经阅读了关于 Hooks 的 React 文档,但我很困惑。 useEffect Hook清理函数什么时候调用?

标签 javascript reactjs react-hooks

关于何时调用 useEffect 清理函数的 React 文档解释令人困惑且老实说是通用的。 他们甚至通过将类心智模型与钩子(Hook)进行比较而使您更加困惑。基于类的组件与带钩子(Hook)的基于函数的组件的工作方式不同。 React 会记住您提供给 useEffect 的效果函数,并在将更改刷新到 DOM 后运行它,这是可以理解的。 现在如何以及何时调用返回的函数(“清理函数”)?

下面的代码示例:

import React, { useState, useEffect } from 'react';

function FriendStatus(props) {
  const [isOnline, setIsOnline] = useState(null);

  useEffect(() => {
    function handleStatusChange(status) {
      setIsOnline(status.isOnline);
    }

    ChatAPI.subscribeToFriendStatus(props.friend.id, handleStatusChange);
    // Specify how to clean up after this effect:
    return function cleanup() {
      ChatAPI.unsubscribeFromFriendStatus(props.friend.id, handleStatusChange);
    };
  });

  if (isOnline === null) {
    return 'Loading...';
  }
  return isOnline ? 'Online' : 'Offline';
}

最佳答案

作为 useEffect 的第一个参数给出的函数返回的函数将在作为第二个参数给出的数组中的任何元素发生变化时调用,或者如果没有给出第二个参数则在每次渲染时调用,或者当组件已卸载。

示例

const { useEffect, useState } = React;

function MyComponent({ prop }) {
  useEffect(() => {
    console.log('Effect!');
    return () => console.log('Cleanup!')
  }, [prop])

  return (
    <div>{prop}</div>
  );
}

function App() {
  const [value, setValue] = useState(0);

  useEffect(() => {
    setInterval(() => {
      setValue(value => value + 1);
    }, 1000)
  }, [])

  return value < 3 ? <MyComponent prop={value} /> : null;
}

ReactDOM.render(<App />, document.getElementById("root"));
<script src="https://unpkg.com/react@16/umd/react.development.js"></script>
<script src="https://unpkg.com/react-dom@16/umd/react-dom.development.js"></script>

<div id="root"></div>

关于javascript - 我已经阅读了关于 Hooks 的 React 文档,但我很困惑。 useEffect Hook清理函数什么时候调用?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/55712446/

相关文章:

javascript - React JS,更新从 map 渲染的特定字段

javascript - 为 React hooks 更新 Javascript 对象中属性的最有效方法

javascript - 计数、间隔和事件的响应式扩展缓冲区

reactjs - Material-ui-next typescript 错误

javascript - TensorFlow JS 异常 - 无法开始训练,因为正在进行另一个 ft() 调用

javascript - 在 React 中捕获获取错误的正确方法?

css - 如何覆盖 material-ui react 组件的 @media css

javascript - 如何每分钟触发一次 React js 组件的重新渲染?

javascript - 使用粘性页脚在弹出窗口调整大小时增加 div 大小

javascript - 如何将 ngTable 上的属性设置变成 promise ?