2013-05-09 64 views
5

當我們開始測試我們的NodeJS項目時,我們注意到了巨大的內存消耗。這是由我們項目中的內存泄漏引起的。所以我們開始尋找可能產生內存泄漏的所有原因。在stackoverflow上有這個問題的一些答案,但是沒有任何關於什麼是內存泄漏的直接文檔。NodeJS中的內存泄漏和關閉問題

我的問題:

  • 是否有V8 GC文檔和它是如何工作(詳細)?
  • 如何釋放回調以便GC可以收集它們?
  • V8 GC是否收集未使用的變量,但是在它們下面有一個函數閉包?例如:

    var serviceChannel = require('./channel'); 
    var dataRegistration = require('../data/registration'); 
    
    function registerOnChannel(userID, channelID, callsuccess, callerror) { 
    
        serviceChannel.findChannel(channelID, function (channel) { 
         if (!channel) { 
          callerror("Channel doesn' exists"); 
          return; 
         } 
         dataRegistration.registerOnChannel(userID, channelID, function (registration) { 
          if (!registration) { 
           callerror("Registration doesn' exists"); 
           return; 
          } 
          callsuccess("Registration successful"); 
         }, function (error) { 
          callerror("Error on registration"); 
         }) 
        }, function (error) { 
         callerror("Error on finding channel"); 
        }) 
    } 
    

所以,serviceChannel和dataRegistration將只要registerOnChanel是現場保存在內存中。但是可變通道是否會被GC刪除(它沒有被任何函數使用)?

+0

「所以,只要registerOnChanel是活的,serviceChannel和dataRegistration就會保存在內存中。你如何得出這個結論? – 2013-05-09 22:57:33

+0

這是一個封閉。 – 2013-05-10 11:30:04

+0

在您發佈的代碼中沒有關閉的證據,至少不會使serviceChannel或dataRegistration保持活動狀態。 – 2013-05-10 11:37:46

回答

0

首先我想說你應該將你的API移動到使用內建的EventEmitterhttp://nodejs.org/api/events.html)。

V8 GC是否收集未使用的變量,但在它們下面有函數閉包?

如果你從以前的功能範圍內使用一個變量,則變量必須堅持圍繞直到包含的功能範圍,以及包含變量的所有回調,已經超出範圍。

但是可變通道是否會被GC刪除(它沒有被任何函數使用)?

根據您發佈的代碼示例,是的,它將由GC收集。但是很可能泄露了一兩個參考而沒有注意到。

+0

我已經測試了NodeJS這個例子的一些變化,GC總是在沒有人引用它們時刪除對象和變量。 我也注意到GC只在需要時運行(懶惰模式)。如果程序消耗了一些內存,它將不會被釋放,直到新的內存分配請求被執行。 V8 GC工作非常好。 – 2013-07-02 09:16:42