執行環境會負責管理代碼執行過程中使用的內存,編寫JavaScript程序時,所需內存的分配以及無用內存的回收完全實現自動管理。
原理:
找出那些不再繼續使用的變量,然後釋放其占用的內存。為此,垃圾收集器會按照固定的時間間隔(或代碼執行中預定的收集時間)周期性地執行這一操作。
垃圾收集的方式:
1.標記清除(mark-and-sweep)
最常用的垃圾收集方式。當變量進入環境時,就將變量標記為“進入環境”。從邏輯上講,永遠不能釋放進入環境的變量所占用的內存,因為只要執行流進入相應的環境,就可能會用到它們。當變量離開環境時,則將其標記為“離開環境”。
立即收集器在運行時會給存儲在內存中的所有變量都加上標記,然後它會去掉環境中的變量以及被環境中的變量引用的變量的標記。剩下的在被加上標記的變量將被視為准備刪除的變量,原因是環境中的變量已經無法訪問到這些變量。最後,垃圾收集器完成內存清除,銷毀那些帶有標記的值並收回它們所占用的內存空間。
2.引用計數(reference counting)
跟蹤記錄每個值被引用的次數,當這個值的引用次數為0時,說明沒有辦法再訪問這個值了,因而就可以將其占用的內存空間回收回來。當垃圾收集器下次再運行時,會釋放那些引用次數為零的值所占用的內存。
(1)應用機制存在一個問題:循環引用。
循環引用是指對象A中包含一個指向對象B的指針,而對象B中也包含一個指向對象A的引用。(這樣它們的引用可能永遠不為0,如果函數被重復多次調用,就會導致大量的內存得不到回收。)
(2)IE中的BOM和DOM中的對象使用C++以COM(component Object Model,組件對象模型)對象的形式實現,而COM對象的垃圾收集機制采用的是引用計數策略。
以下是COM對象導致的循環引用的問題:
eg:
var element=document.getElementById("some_element"); var myObject=new Object(); myObject.element=element; element.someObject=myObject;
上面的例子在一個DOM元素(element)和一個原生JavaScript對象(myObject)之間創建了循環引用。由於存在這個循環引用,即使將例子中的DOM從頁面移除,它也永遠不會被回收。
可以使用以下代碼手工斷開原生JavaScript和DOM元素之間的鏈接:
myObject.element=null; element.someObject=null;
以上就是本文的全部內容,希望本文的內容對大家的學習或者工作能帶來一定的幫助,同時也希望多多支持!