1
JVM中的存儲空間分為堆(heap)和棧。堆呢,放程序運行過程中創建的對象,而棧呢主要放static方法與static 變量.
堆內存中又分為兩個區。新對象區,和老對象區。新對區又分為三個小區:伊甸園區,From區,To區。伊甸園區用來存放新創建的對象。當伊甸園區放滿后,JVM系統做達到性測試,主要檢測那些由根集合出發而不可到達的,這此對象被JVM回收。并且將所有活動對象從伊甸園區拷貝到To區,此時一些對象從發生狀態變化。有此對象從To區域被拷貝到From區域,此時From區域就有對象。整個過程都是由JVM來完成的。
老對象區域中的對象仍然有一個較長的生命周期。大多數JVM系統垃圾對象,都來源于“短命”對象,經過一段時間后被轉入老對象區域,就成了垃圾對象。
2 JVM中對象的生命周期
??? 對象整個生命周期分為七個階段:創建階段,應用階段,不可視階段,不可到達分階段,可收集階段,終結階段,釋放階段。
?? 對象的創建要經過以下5個步驟的:
??? 1)為對象創建空間
??? 2)開始構造對象
??? 3)遞歸調用其超類的構造方法
??? 4)進行對象實例初始化和變量初始化
??? 5)執行構造方法體
對象創建原則:
??? 1) 避免在循環體中創建對象。
??? 2) 盡量及時使對象符合垃圾回收標準
??? 3) 不要采用過深層次繼承
??如:
? for(int i=1;i<1000;i++){
??? Object o=new Object();
? }
執行的效率遠比不上。
? Object o=null;
? for(int i=0;i<1000;i++){
????? o=new Object();
?}
采用這種方式,僅在內存中保存一份該對象的引用。
而不像上面的方法產生大量的對象。浪費大量內存,添加了垃圾回收的負擔。
在程序設計中要做到“勿以惡小而為之”
?
對象應用階段:
???? 一個應用階段的對象應具備以下特征:
?????? 1) 系統至少維護著對象的一個強引用
?????? 2) 所有對該對象的用都是強引用,除了我們顯式地使用了軟引用,弱引用和虛引用外。
??? 強引用:是指從JVM根集出發遍尋堆中所有到達對象的路徑,
??? 軟引用:當內存不足時才回收這類內存,因為當內存足夠時通常不回收,適合較長生命周期對象。
??? 弱引用:弱引用對象最容易被GC回收。一旦弱引用置為NULL時,這個對象引用就不存在了,GC能夠回速回收該對象的空間。如
?? import java.lang.ref.WeakReference;
?? A a=new a();
? //把a至為弱引??? 用
? WeakReference wr=new WeakReference(a);
? a=null;
? if(wr!=null){
???? a=wr.get();
? }else{
???? a=new A();
???? wr=new WeakReference(a);
? }
不可視階段
???? 說明我們在其它區域已經不可以再引用它。如本地變量的引用,例子略。
不可到過階段
??? 找不到的對象,
可收集階段,終結階段和釋放分階段
??? 在這個階段的對象具有以下特征:
???? 1 回收器發現該對象不可到達。
???? 2 finally 方法已被執行
???? 3 對象空間已被重用
JAVA的析構方法finalize
類似于C++的析構函數。通常我們在程序的最后使用用super.finalize()來實現從下到上的finalize的調用。通常我們在finalize方法中釋放一些非常重要的資源如:I/O操作,數據庫連接。由于GC調用finalize的時間是不確定的,我們需要通過其它手段釋放其占用的資源如:
public ?Class? A{
??? Object a=null;
????public A(){
????? System.out.println("創建對象A");
????? a=new Object();
??? }
?? proctected void destroy(){
???? a=null;
???? System.out.println("釋放a對象");
?? }
?proctected void finalize() throws? java.lang.Throwable{
???? destroy();
????? super.finalize(); //遞歸調用超類的finalize()
?}
}
JAVA程序設計中有關內存的管理經驗:
? 1?不再使用的變量要盡早將不用的對象賦為NULL,這將加速GC的工作。
?2?? 盡量少用finalize函數,因為它會加GC的工作量。
?3? 如果經常用到圖片,可以使有soft引用類型。這樣能防止memory outof
4??注意使用集合數據類型,因為數組,樹,圖。對GC來說回收更復雜,注意一些static 和全局變量,因為往往容易引起懸掛對象和內存浪費。
5 盡量避免在類的權造器中創建初始化大量對象。
6 避免強制系統做垃圾回收(顯式調用方法System.gc())
7?盡量避免顯式申請數組空間。
8 盡量用對象池。
??
posted on 2006-04-11 10:55
有貓相伴的日子 閱讀(254)
評論(0) 編輯 收藏 所屬分類:
j2ee