繼承建立「子類是父類的一種」關係,子類自動擁有父類非私有成員,可新增、覆寫、擴展。關鍵字 extends,Java 單繼承(類),多實現(介面)。
public class Animal {
protected String name;
public void eat() { System.out.println(name + " 進食"); }
}
public class Dog extends Animal {
// 1. 覆寫 @Override:編譯期檢查簽名一致,防誤寫成重載
@Override
public void eat() {
super.eat(); // 調用父類實現
System.out.println("狗狂吞虎嚥");
}
// 2. super 調用父構造器(必須首行)
public Dog(String name) {
super(); // 隱式調用父無參構造器;父無無參構造器必須顯式 super(...)
this.name = name;
}
}
| 維度 | 重載 | 覆寫 |
|---|---|---|
| 發生位置 | 同一類 / 父子類 | 父子類之間 |
| 方法簽名 | 名稱相同,參數列表不同 | 名稱、參數、返回類型完全一致 |
| 返回類型 | 可不同 | 协變返回類型(子類型) |
| 拋出異常 | 無限制 | 子類異常 ⊆ 父類異常 |
| 訪問權限 | 無限制 | 子類權限 ≥ 父類權限 |
| 綁定時機 | 編譯期靜態綁定 | 運行期動態綁定(多態核心) |
Animal a = new Dog(); // 向上轉型:子類對象賦值給父類引用
a.eat(); // 動態分派:調用 Dog.eat()
a.name = "旺財"; // 僅能訪問 Animal 定義的成員
// a.bark(); // 編譯錯誤:父類引用不可訪問子類特有方法
向上轉型安全:父類引用指向更具體子類對象,不會丟失父類成員。向下轉型需 instanceof 守衛。
Has-a 關係更靈活,通過介面委託實現復用(策略模式、裝飾器模式)。@implSpec 標註可覆寫方法的契約,或用 final 禁止覆寫/繼承。子類構造器首行隱式/顯式 super() 保證父對象先構造完成。
ArrayList is-a List)。其他場景優先考慮組合、介面、委託。