javascript - 回调函数内声明的变量是否保留在内存中,还是在回调执行结束时被销毁?

标签 javascript node.js memory theory ram

我有这个代码片段;它基本上连接到 mongo 数据库并浏览文档。在每次迭代中,它都会搜索消息对象数组。它创建消息变量,然后循环遍历它。 回调函数内声明的变量 (var msg) 是否保留在内存中,还是在回调函数执行结束时被销毁?如果 var msg 实际上被声明为 let msg?有没有办法从内存中丢弃整个范围?

MongoClient.connect(mongoUrl, (err, db) => {
  assert.equal(null,err);
  var collection_data = db.collection('threadContents').find();
  collection_data.on('data', (doc) => {
    var msg = doc.messages;
    for (var variable in msg) {
      console.log(msg);
    }//forin(msg)
  });//collection_data.on
});//mongo.connect

最佳答案

理论上 - 是的。
实际上 - 事情没那么简单......

在您的示例中,var msg 不会“泄漏”到其原始范围之外,因此当回调完成其工作时它很可能会被销毁。
需要注意的一件事 - 这个对象的销毁不必立即发生 - JS 引擎大多是垃圾收集的,因此这 block 内存可以在堆栈上保留一段时间,但将不再可访问。

如果您要在外部作用域中声明此变量,并且该作用域保留在内存中,则它可能会保留在内存中(因此,其他代码片段可以访问该变量)。您可以在Closures中阅读有关此行为的信息。 MDN 部分。

另一件事需要注意的是console.log的使用。一般来说,非原始值(例如对象或数组,它们实际上是“特殊”对象)可以通过引用而不是值来访问。因此,如果您的 var msg 是非基元,它很可能会保留在内存中,直到您清除控制台。原始值将被复制,因此严格来说,它们仍然会保留在内存中,但可能会保留在内存中的另一个位置(尽管 JIT 引擎可能会尝试优化它,并且如果不需要,则不会复制内存)。

关于javascript - 回调函数内声明的变量是否保留在内存中,还是在回调执行结束时被销毁?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39306225/

相关文章:

javascript - 将 script.js 链接到 html

javascript - umi 请求拦截器响应的刷新 Token

javascript - 在括号内使用点会破坏 swig 模板

c++ - 如何将 wchar_t 转换为 V8 字符串?

java - 如何分析 Java 1.3 中的内存泄漏

javascript - CKEditor autogrow插件垂直滚动条闪烁问题

javascript - d3js 强制按钮允许/禁用拖动操作

json - 如何更改 package.json 中的名称属性?

c - 看不见的内存泄漏? - malloc 和 strcpy

php - PHP 在不相关的代码上浪费了多少资源(如果有的话)?