【问题标题】:Node.js stream pipes and garbage collectionNode.js 流管道和垃圾收集
【发布时间】:2017-05-07 14:13:48
【问题描述】:

问题: 在 Node.js 中,如果 Readable 流通过管道传输到 Writable 流并且都超出范围,那么在阅读器完成之前,这对流是否容易被垃圾收集? (因为它们现在无法访问)

背景: 我试图了解管道对流对象生命周期的影响。我在假设管道代表两个流之间的双向引用的情况下进行操作,因此如果一个可访问,则两者都不会被垃圾收集(当然,直到读取器结束并且管道关闭)。

所以有了这个假设:运行时中是否有任何东西在管道处于活动状态时保持流存在,或者当 Readable 上的“数据”侦听器正在执行等效操作时? (除了显而易见的,比如嵌入在事件监听函数和其他对象中的引用)

一个具体的例子是将一个文件读取流通过管道传输到一个 http 响应对象。如果我“一劳永逸”,并且不保留对文件或响应流的引用,这个过程是否会在中途中断?

或者,如果某些东西阻碍了管道流的 GC,那么两个套接字之间的双向管道是否会无限期地存在,即使它们都无法访问? (并且完全无法关闭?)

【问题讨论】:

  • 我的想法是这取决于流的类型。如果您正在使用其源和接收器在内存中的各种可读/可写流,那么我想如果没有对它们的引用,它们可以随时被 GC-ed。但是,处理操作系统资源的流可能会表现不同并且可能会一直存在。 (我不确定,所以这是评论,而不是答案。)不管行为如何,我认为管道和忘记是不好的形式,因为这会使错误处理、测试和其他操作变得更加困难好东西。
  • 我听到你在说什么,但是如果你看一下 http 文件服务器的一般教程示例,它们通常会管道然后让两个流都超出范围。此外,即使是普通的通用流也可能是一个转换流,它位于从一个操作系统资源流到另一个操作系统资源流的链式管道中间(例如,读取文件,通过我的转换管道,发送到 http 响应),所以如果进程要成功,管道必须能够阻止 GC。还是我错过了什么?
  • 你可能是对的。我对我现在所说的没有多少信心。 :) 但我也没有看到任何有明确解释的东西。期待一个。

标签: node.js stream garbage-collection pipe


【解决方案1】:

和往常一样,答案是:视情况而定。

如果没有引用流对象,那么它们将被垃圾回收。但是,可能在您的代码之外的其他地方有引用。

请注意,可读流通过事件处理程序引用可写流,因此我们真正需要的是对可读流的引用以保持两者都处于活动状态。

如果源是一个能够自行生成数据的流(它从文件、网络或内存中的某物读取)并且管道正在流动,那么它被某个地方的回调引用(I/O 延续、事件处理程序或给setTimeout()process.nextTick() 的闭包)。

如果源是等待您将数据推送到其中的流或管道已暂停,则可能没有引用,并且两个流最终都将被垃圾收集。

【讨论】:

    猜你喜欢
    • 2011-07-16
    • 2019-02-22
    • 2018-04-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-08-01
    • 2012-11-30
    • 2010-10-04
    相关资源
    最近更新 更多