Javascript內存泄露
1.什么是內存泄露?
內存泄露是指分配給應用的內存不能被重新分配,即使在內存已經不被使用的時候。正常情況下,垃圾回收器在DOM元素和event處理器不被引用或訪 問的時候回收它們。但是,IE的早些版本(IE7和之前)中內存泄露是很容易出現的,因為內存管理器不能正確理解Javascript生命周期而且在周期 被打破(可以通過賦值為null實現)前不會回收內存。
2.為什么你需要注意它?
在大型Web應用程序中內存泄露是一種常見的意外編程錯誤。內存泄露會降低Web應用程序的性能,直到浪費的內存超過了系統所能分配的,應用程序將 不能使用。作為一Web開發者,開發一個滿足功能要求的應用程序只是第一步,性能要求和Web應用程序的成功是同樣重要的,更何況它可能會導致應用程序錯 誤或瀏覽器崩潰。
3.Javascript中出現內存泄露的主要原因是什么?
1)循環引用
一個很簡單的例子:一個DOM對象被一個Javascript對象引用,與此同時又引用同一個或其它的Javascript對象,這個DOM對象可 能會引發內存泄露。這個DOM對象的引用將不會在腳本停止的時候被垃圾回收器回收。要想破壞循環引用,引用DOM元素的對象或DOM對象的引用需要被賦值 為null。
2)Javascript閉包
因為Javascript范圍的限制,許多實現依賴Javascript不包,請查看我的前面的文章JavaScript Scope and Closure如果你想了解更多閉包方面的問題。
閉包可以導致內存泄露是因為內部方法保持一個對外部方法變量的引用,所以盡管方法返回了內部方法還可以繼續訪問在外部方法中定義的私有變量。對Javascript程序員來說最好的做法是在頁面重載前斷開所有的事件處理器。
3)DOM插入順序
當2個不同范圍的 DOM 對象連添加到一起的時候一個臨時的對象會被創建。這個DOM對象改變范圍到document時,那個臨時對象就沒用了。也就是說, DOM 對象應該按照從當前頁面存在的最上面的 DOM 元素開始往下直到剩下的 DOM 元素的順序添加,這樣它們就總是有同樣的范圍,不會產生臨時對象。
4)如何檢測?
內存泄露對開發者來說一般很難檢測因為它們是由一些大量代碼中的意外的錯誤引起的,但它在系統內存不足前并不影響程序的功能。這就是為什么會有人在很長時間的測試期中收集應用程序性能指標來測試性能。
最簡單的檢測內存泄露的方式是用任務管理器檢查內存使用情況。在Chrome瀏覽器的新選項卡中打開應用并查看內存使用量是不是越來越多。還有其他的調試工具提供內存監視器,比如Chrome開發者工具。這是谷歌開者這網站中的堆分析的特性的教程。
參考:
1. http://javascript.crockford.com/memory/leak.html
2. http://msdn.microsoft.com/en-us/library/Bb250448
3. http://www.ibm.com/developerworks/web/library/wa-memleak/