JavaScript內存泄露

jopen 9年前發布 | 11K 次閱讀 JavaScript開發 JavaScript

原文出處: Memory leaks   譯文出處: 韓子遲   

譯者前言

原文地址:Memory leaks

最近簡單了解了下JavaScript的閉包和垃圾回收機制(GC),這中間也不得不接觸內存泄露這個概念。然后不小心找到了這篇文章,看下來后理解了不少東西,于是譯之與大家分享。

在JavaScript中,我們很少考慮到內存管理,但是它又是真實存在的。當我們創建一個變量,接著使用它們,然后瀏覽器的垃圾回收機制對它們進行回收。

雖然我們很少考慮內存管理,但是當應用程序越來越復雜并且ajax化之后,我們打開一個網頁,過段時間發現瀏覽器消耗的內存不斷增大,很有可能是因為內存泄露,這時我們不得不考慮內存管理。

JavaScript的內存管理

JavaScript內存管理的核心也就是JavaScript垃圾回收機制,而存在在內存中的數據包括堆棧中的數據(局部變量,正在被調用的方法的參數)以及全局變量;而對象如果被引用或者存在在一個引用鏈中時,也會存在在內存中。關于這點可以參考JavaScript垃圾回收機制。

下面再舉個GC的例子:

</div>

</div>

</div>

</div>

</div> JavaScript </div> </div>

function Menu(title) { this.title = title this.elem = document.getElementById('id') } var menu = new Menu('My Menu') document.body.innerHTML = '' // (1) menu = new Menu('His menu') // (2)

1

2

3

4

5

6

7

8

9

10
</div> </td>

function Menu ( title ) {

   this . title = title

   this . elem = document . getElementById ( 'id' )

}

 

var menu = new Menu ( 'My Menu' )

 

document . body . innerHTML = ''    // (1)

 

menu = new Menu ( 'His menu' ) // (2)
</div> </td> </tr> </tbody> </table> </div> </div>

內存結構如下:

JavaScript內存泄露

在step(1)后,body.innerHTML被清空了,所以它的子節點都被移除了。但是元素#id是個例外,它依然能通過menu.elem訪問,所以它依然存在在內存中,當然如果你無法訪問它的父節點,因為它被移除了。

單個的dom元素可能存在在內存中哪怕它的父節點已經被移除。

在step(2)后,window.menu被重新賦值引用,所以原來的menu不可訪問了,于是自動被GC回收。

JavaScript內存泄露

而閉包經常會引起循環引用:

 本文由用戶 jopen 自行上傳分享,僅供網友學習交流。所有權歸原作者,若您的權利被侵害,請聯系管理員。
 轉載本站原創文章,請注明出處,并保留原始鏈接、圖片水印。
 本站是一個以用戶分享為主的開源技術平臺,歡迎各類分享!
  • sesese色