java之多型(java程式設計思想筆記)
(摘自看過的書籍與部落格)
多型是指在程式中定義的引用變數所指向的具體型別和通過該引用發出的方法呼叫在程式設計時並不確定,而是在程式執行期間才確定,即一個引用變數到底會指向哪個型別物件,該引用變數發出的方法呼叫到底是哪個類中實現的方法,必須由程式執行期間才能確定。因為在執行時才能確定的類,不用修改程式碼,就可以讓引用變數繫結到各種不同的類實現上,從而導致該引用呼叫的具體方法隨之改變,即不修改程式程式碼就可以改變程式執行時所繫結的具體實現類,讓程式可以選擇多個執行狀態。多型通過分離做什麼和怎麼做,從另一角度將介面和實現分離開來。
1.向上轉型
物件既可作為它自身使用,也可作為它的基類使用。而這種把某個物件的引用視為對其基型別的引用的做法稱為向上轉型。
2.方法呼叫繫結
將一個方法呼叫同一個方法主體關聯起來被稱作繫結。在執行時根據物件的型別進行繫結稱為執行時繫結或動態繫結。它可保證其產生正確的行為(即呼叫正確的具體實現方法)
interface A{
void method1();
void method2();
}
interface Factory{
A getA();
}
class B implements A{
public void method1(){
System.out.println("class B method1");
}
public void method2(){
System.out. println("class B method2");
}
}
class C implements A{
public void method1(){
System.out.println("class C method1");
}
public void method2(){
System.out.println("class C method2");
}
}
class BFactory implements Factory{
public A getA(){
return new B();
}
}
class CFactory implements Factory {
public A getA(){
return new C();
}
}
public class Test{
public static void doComsuer(Factory factory){
A a = factory.getA();
a.method1();
a.method2();
}
public static void main(String[] agrs){
doComsuer(new BFactory());
doComsuer(new CFactory());
}
}
//out
class B method1
class B method2
class C method1
class C method2
3.可擴充套件性:
通過從通用的基類繼承出新的型別,新增一些功能,那些操作基類介面的方法不需要任何變動就可以應用於新類。
4.初始化順序
基類靜態程式碼塊
子類靜態程式碼塊
基類非靜態程式碼塊
基類靜態屬性
子類靜態屬性
基類普通屬性
基類構造方法
子類普通屬性
子類非靜態程式碼塊
子類構造方法
5.清理
清理順序與初始化順序相反,首先對其匯出類進行清理,然後才是基類。
6.構造器內部的多型方法的行為
編寫構造器是:“用盡可能簡單的方法使物件進入正常狀態,避免呼叫其它方法”。如果基類中呼叫子類中也重寫的方法,會指向子類中的方法,子類因為沒有初始化而可能導致結果出錯。
7.用繼承進行設計
用繼承表達行為上的差異,並用欄位表達狀態上的變化。
8.向下轉型
執行時型別識別,轉型出錯會報“ClassCastException”異常(型別轉換異常)。可用instanceof進行判斷。
多型意味著“不同的形式”,在面向物件的程式設計中,我們持有從基類繼承而來的相同介面,以及使用介面的不同形式:不同版本的動態繫結。