学习笔记2——对象初始化和面向对象特性
1.java類的初始化順序:
(1).在一個類中,初始化順序由變量在類中的聲明定義順序決定,成員變量(非set方法和構造方法的初始化)的初始化發生在方法調用之前,包括構造方法。
(2).靜態變量在整個存儲區只保留一份拷貝,本地變量不能使用靜態關鍵字,基本類型的靜態變量不需要初始化,它會根據類型獲得初始化值,引用類型的靜態變量默認初始化為null。
靜態變量的初始化發生在需要使用的時候,一旦被初始化之后,靜態變量就不會再初始化。
(3).靜態初始化塊和靜態變量類似的執行也在構造方法之前,并且僅執行一次。
(4).動態初始化塊(與靜態初始化塊類似,只是沒有static關鍵字,即放在一對大括號中的代碼塊)在靜態初始化塊初始化結束后執行,動態初始化塊每次創建新對象都會初始化一次。
(5).構造方法執行時,先執行父類的構造方法,后執行子類的構造方法。
(6).本地變量初始化最晚,在方法中初始化。
綜述,類的初始化順序依次為:
a.父類的靜態變量/靜態初始化塊;
b.子類類的靜態變量/靜態初始化塊;
c.父類的動態初始化塊、非構造方法和set方法的成員變量初始化
d.子類的動態初始化塊、非構造方法和set方法的成員變量初始化
e.父類的構造方法。
f.子類的構造方法。
g.父類本地變量。
h.子類的本地變量。
2.數組初始化:
Java中數組初始化有以下3中方式:
(1).數組聲明時直接初始化,如:
int[] a = {1,2,3};
(2).動態數組初始化,如:
int[] a = new int[]{1,2,3};
注意:動態數組初始化時,不能在new()操作符中指定數組的大小,即int[] a = new int[3]{1,2,3}的寫法是錯誤的,數組的大小由初始化數組元素個數決定。
(3).固定長度數組初始化,如:
int[] a = new int[3];
a[1] = 0;
a[2] = 1;
a[3] = 2;
注意:固定長度大小的數組初始化時不能大于所聲明的數組長度,沒有聲明的數組元素使用其默認值,如int默認為0,對象類型的值為引用,默認為null.
3.java代碼重用4中方式:
java面向對象編程中提供了如下4中代碼重用的方式:
(1).組合:
面向對象編程中最常用的代碼復用方式,具體的方式是在一個對象中將另一個對象引用最為成員變量,其最大的優點是既實現松散耦合,有可能提高代碼復用率。
(2).繼承:
面向對象編程中常用的提高代碼復用率的方法之一,適用于子類和父類是同一種抽象類型,具有共同的屬性情況。
使用繼承,子類可以復用父類除private私有房屋控制權限以為的所有屬性和方法,編譯器將父類封裝為子類對象內部的一個對象。
需要注意的是:調用子類初始化構造方法時,編譯器會確保首先調用父類的構造方法初始化父類,然后才初始化子類,如果父類中沒有默認的構造方法,即需要顯式傳入參數的構造方法時,子類必須通過super關鍵字顯式傳入參數調用父類的構造方法。
(3).委派:
Java中不支持委派方式的代碼復用,但是開發人員可以使用委派機制實現代碼的重用。
委派是指,java對象的所有方法其實都是委派調用另一個類的方法實現,但是當前類又不是所委派類的類型,因此使用繼承不太合適,解決方式和組合類似,將被委派類作為委派類的成員變量,委派類的方法直接調用被委派類對象應用的方法。
如:
[java]?view plaincopy(4).聯合使用組合和繼承方式:
因為java中不允許多繼承,如果某種情況下,一個java類需要使用多個其他類功能,且該類和其中某個類具有很多共同屬性,即可以看作同一類,則可以使當前類繼承具體共同屬性的類,同時將其他類作為成員變量組合引用。
4.組合和繼承的區別:
組合和繼承都可以復用代碼,很多java程序員,甚至是架構師都分不清楚什么情況下該使用組合,什么情況下應該使用繼承,具體的區別如下:
(1).組合:
組合通常是在一個類中想使用另一個類已有的特性,但是卻不想使用其接口。
使用組合可以可以將一個類作為當前類的內嵌對象,這樣在當前類中就可以顯式地使用內嵌類已經實現的功能,與此同時又不會影響當前類的調用接口。
(2).繼承:
繼承是隱式地使用被繼承類的功能,相當于提供了一個新版本的父類實現。
使用繼承,子類不但可以復用父類的功能,同時還復用了父類的接口,子類和父類的對外調用接口相同的情況下適合使用繼承。
使用繼承時,很多情況下需要向上類型轉換,即將子類看作其父類。在編程時到底選用組合方式還是繼承方式,一個簡單的判斷依據是:是否需要向上類型轉換,如果需要就使用繼承,如果不需要,則選擇組合。
5.final方法:
Java中使用final類型的方法有以下兩種原因:
(1).設計原因:
final類型的方法不允許其子類修改方法,即不允許子類覆蓋父類的final方法。
(2).效率原因:
在早期的java實現中,如果方法被聲明為final,編譯器將final方法調用編譯為內聯調用。
正常的方法調用是:如果方法調用時,將當前的方法上下文保持到棧中,調用被調用的方法,然后在將調用上下文出棧恢復調用現場。
內聯調用是:如果方法調用時,將被調用方法體拷貝到當前調用的地方合并成一個方法體,這樣就避免因需要保存方法調用線程而進行的進棧和出棧操作,可以提高效率。
新版的使用hotspot技術的java虛擬機可以探測方法調用情況而做效率優化,final方法不再作為提高效率的手段,唯一的作用是確保方法不被子類覆蓋。
注意:任何private的方法都是隱式的final類型,同final方法類似,private方法不能被子類所覆蓋,但是private比final更嚴格,基類的private方法對子類不可見,private方法不再是接口的一部分。
6.多態性:
面向對象編程中的多態和繼承往往是一起發揮作用的,使用繼承,所有的子類和父類使用相同的對外接口,而多態的基礎是晚綁定或動態綁定或運行時綁定,即對象引用使用基類類型,在編譯時編譯器無法確切知道到底調用哪一個具體類,只有在運行時,java虛擬機才通過類型檢查確定調用對象的具體類型。
Java中默認對象引用全部是晚綁定,只有static和final類型的引用時早綁定或編譯時綁定。
多態的優勢是:程序的可擴張性好,無論添加多少個子類,基類的接口都不用改變,只需要在子類對應方法中提供具體實現即可,也就是所謂的將程序變化的部分和程序保持不變的部分分離。
注意:只有正常的方法可以使用多態,字段和靜態方法沒有多態機制。
?????? ? 構造方法也不支持多態機制,構造方法是隱式的static聲明。
總結
以上是生活随笔為你收集整理的学习笔记2——对象初始化和面向对象特性的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Java注释(Annotation)详解
- 下一篇: 《Java编程思想》学习笔记4——集合容