我很确定我有内存泄漏。当我重复执行某些操作(例如打开菜单),然后使用 3 个堆快照技巧时,总是会泄漏内存。每次的保持器都不一样。我禁用了 React Devtools 并尝试了生产构建,但仍然出现内存泄漏。
我花了两天时间试图解释结果,但我仍然不知道这意味着什么。例如。这是内存泄漏的示例:
如果有人知道以下任何问题的答案,那就太好了:
将其解释为是否正确:
HTMLInputElement
以某种方式引用了调用useContext
的函数?
保留器中的“instruction_stream”、“previous”和“context”是什么意思?
我知道“(编译代码)”意味着它是 V8 创建函数的优化版本。然而,Chrome 似乎多次生成“useContext”的新优化版本?我多次重复了 3 堆技巧,并且“useContext”每次都在那里。
我在哪里可以找到更多关于“(代码重定位信息)”,“(代码deopt数据)”,“(源位置表)”等含义的信息?
我也希望有一些关于内存快照中使用的所有奇怪术语的良好文档,但我不知道其中一个,所以接下来的内容主要是最好的猜测。
这是我阅读屏幕截图的方式(主要是底部):
<input>
value
属性是在 react-dom.development.js
第 1652 行定义的 getter(看一下,它实际上只是原生 getter 的包装)context
所指的,闭包可以访问的变量。
HooksDispatcherOnUpdateInDEV
(在 React 内部定义),它又指的是
useContext
。
instruction_stream
、
previous
和
context
可能是V8源代码内部使用的单词。我在上面解释了
context
,
previous
肯定是一个实现细节,也许上下文被定义为嵌套上下文的链接列表,你需要更进一步。
instruction_stream
可能是实际编译指令的存储位置。如果您了解 V8 如何实现的更多技术细节(我不知道),
(code relocation info)
、
(code deopt data)
、
(source position table)
可能又会有意义。但是这里有两个想法可以帮助您进一步进行调试:
首先,在我看来,内存泄漏不太可能仅仅是因为编译了太多代码。通常内存泄漏是由于某些实际的 Javascript 对象(或 DOM 元素)被泄漏造成的,所以我建议您尝试在内存快照中查找这些对象。
但最重要的是,
分析应用程序的生产版本,而不是开发版本!
React 的开发版本很可能包含“故意”内存泄漏,例如为了使 React 开发工具正常工作,因此尝试分析它根本没有帮助。祝你好运!