javascript - React useEffect 清理函数运行多次?

标签 javascript reactjs react-hooks

React hook 新手...

给定这个例子

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);
    };
  });

来自文档

React performs the cleanup when the component unmounts. However, as we learned earlier, effects run for every render and not just once. This is why React also cleans up effects from the previous render before running the effects next time.

这是否意味着 unsubscribeFromFriendStatus仅在组件卸载或每次渲染时运行一次?

扩展我的问题:

如果unsubscribeFromFriendStatus每次都会运行,跳过它的唯一方法是使用可选的第二个参数...那么它不会更难实现 componentWillMount 的原始显式执行吗?和 componentWillUnmount ?说,我要 subscribe什么时候componentWillMount , 并且只运行 unsubscribe什么时候componentWillUnMount

最佳答案

Does that mean unsubscribeFromFriendStatus only gets run when once when component unmounts or every render?

unsubscribeFromFriendStatus 运行每次重新渲染

每次重新渲染,即使 props.friend.id 从未改变,它也会取消订阅并重新订阅。

要改善这一点,请仅在 props.friend.id 更改时运行效果。 这可以通过将其添加为 useEffect() 的依赖项来实现。

useEffect(
  () => { /* subscription */ }
  , [props.friend.id] // add as dependency
)

doesn't it make it harder to implement the original explicit execution of componentWillMount and componentWillUnmount? Say, I want to subscribe when componentWillMount, and only run unsubscribe when componentWillUnMount?

使用 props.friend.id 的旧值维护旧订阅没有意义。

订阅使用资源(websocket 或观察者)。在 componentWillUnmount 期间取消订阅时,只会取消订阅 props.friend.id 的最新值。

旧订阅会怎样?没有被释放。 因此,您有一个内存泄漏

关于javascript - React useEffect 清理函数运行多次?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58424470/

相关文章:

javascript - React 上下文每次使用它时都会返回初始状态 - 尽管 setState

reactjs - 将对象替换为 React 状态下的另一个对象

使用 `new Function()` 优化 Javascript

javascript - 根据屏幕尺寸/媒体查询更改 Bootstrap 列类属性

javascript - Dhtml 转换

javascript - 评分系统JavaScript不会将结果发送到Firebase

javascript - 从 NESTED 对象数组中删除重复项

reactjs - 如何使用 MenuItem 进行导航? Material -ui V1

reactjs - antd - 表单输入动态验证

javascript - useEffect 导致组件无限重新渲染