根搜索算法:這個算法的基本思路是通過一系列名為“GC roots”的對象作為起點,從這些節點開始向下搜索,搜索走過的路徑稱為引用連,當一個對象到GC roots沒有任何引用鏈,則證明對象是不可用的。將被判定為可回收對象。不可達對象要被垃圾回收,至少要經歷兩次標記過程。第一次標記時執行finalize()方法,並做記號,第二次標記則不會再執行finalize()方法了。執行finalize()方法后,對象可能又變為可達對象,逃脫被垃圾回收的命運。
示例代碼--周志明著 Java虛擬機
1 public class FinalizeEscapeGC { 2 3 public static FinalizeEscapeGC SAVE_HOOK = null; 4 public String name; 5 public FinalizeEscapeGC(String name) { 6 this.name = name; 7 } 8 public void isAlive() { 9 System.out.println("yes, i am still alive"); 10 } 11 @Override 12 protected void finalize() throws Throwable { 13 super.finalize(); 14 System.out.println("finalize method executed!"); 15 System.out.println(this.name); 16 FinalizeEscapeGC.SAVE_HOOK = this; 17 } 18 public static void main(String[] args) throws Throwable { 19 SAVE_HOOK = new FinalizeEscapeGC("abc"); 20 SAVE_HOOK =null; 21 System.gc(); 22 Thread.sleep(500); 23 if(SAVE_HOOK != null) { 24 SAVE_HOOK.isAlive(); 25 } else { 26 System.out.println("no, i am dead"); 27 } 28 29 SAVE_HOOK =null; 30 System.gc(); 31 Thread.sleep(500); 32 if(SAVE_HOOK != null) { 33 SAVE_HOOK.isAlive(); 34 } else { 35 System.out.println("no, i am dead"); 36 } 37 } 38 }
第21行,第一次垃圾回收,名為abc的FinalizeEscapeGC實例對象的finalize()方法執行,此時全局靜態變量 SAVE_HOOK又重新指向了改對象,使得該對象“復活”,
第29行,再次切斷引用鏈,30行,第二次垃圾回收,該對象的finalize()方法不會再執行了。該對象在堆中的空間被釋放。