reactjs - React useEffect Hook return () => cleanup() 与 return cleanup

标签 reactjs use-effect codemirror

我对 useEffect 的清理回调函数有疑问。简而言之,return cleanup 会出错,但 return () => cleanup() 效果很好。是的,它们是不同的,但是它们有什么不同呢?有谁知道如何解释吗?谢谢,

我在使用 codemirror 编写时遇到了这个问题。

我看到的错误消息是

Unhandled Runtime Error
TypeError: Cannot read properties of undefined (reading 'plugins')

我的钩子(Hook)

export const useCodeMirror = () => {
  const state = ...
  const parent = ...
  
  useEffect(() => {
    const view = new EditorView({state: state, parent: parent})
    // return view.destroy raises an error
    return () => view.destroy()  // works perfectly
  }, [element])
}

node_modules/@codemirror/view/dist/index.js L:6740-6750

    destroy() {
        for (let plugin of this.plugins)
            plugin.destroy(this);
        this.plugins = [];
        this.inputState.destroy();
        this.dom.remove();
        this.observer.destroy();
        if (this.measureScheduled > -1)
            cancelAnimationFrame(this.measureScheduled);
        this.destroyed = true;
    }

package.json

{
  "dependencies": {
    ...
    "codemirror": "^6.0.1",
    ...
  }
}

最佳答案

通常可以直接返回清理函数,而不是将其包装在附加的箭头函数中。在这种情况下需要附加函数的唯一原因是 destroy 使用 this

对于常规函数,this 的值由函数的调用方式决定。因此,如果您的代码显示 view.destroy(),那么字符 view. 就是 this 设置为 的原因查看。这就是 () => view.destroy() 有效的原因:在调用该函数时,您明确说明了 this 应该是什么。

但是如果你只是返回view.destroy,你就没有调用该函数,只是返回它的引用来使用react。 React 对 view 一无所知,它只知道你返回了一个函数。因此,当 React 稍后调用您的函数时,它不知道将 this 设置为什么,因此 this 被设置为未定义。由于它未定义,this.plugins 会导致您看到的错误。

关于reactjs - React useEffect Hook return () => cleanup() 与 return cleanup,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/73569392/

相关文章:

css - 如何将主 .scss 文件加载到 Webpack 3.6~ 和 React

reactjs - 如何阻止 useEffect hook React 中的内存泄漏

javascript - 如何在 CodeMirror 3 中设置嵌套代码块的样式

不带参数或括号的 JavaScript 切片(CodeMirror sql-hint.js 中的代码)

javascript - 数据增加时如何自动生成声音代码

reactjs - 如何将 HTML 元素传递给 React 中的高阶函数 (HOC)?

reactjs - Material 用户界面 : use media query outside component

reactjs - React Hook useEffect 缺少依赖项 Props

reactjs - 应用程序 useEffect 未通过 react 路由器触发

jQuery 热键...不是那么全局化