JAVA的覆蓋、繼承和多態的詳細解說.this和super的用法
關鍵字: java 覆蓋 多態 繼承 this super
Java代碼
1. 繼承:
(1)子類的構造方法一定會調用父類的構造方法。
(2)任何子類構造方法第一行肯定是this();或者super();兩個擇一。
this();調用本類的其它構造方法。(傳遞相應參數調用相應的方法)
super();調用父類的構造方法。
2. 覆蓋:
子類覆蓋父類前提:
(1) 同名,同參數列表,同返回類型。
(2) 子類覆蓋後的方法的訪問權限只能比父類相同或者更寬廣。
(3) 子類覆蓋後的方法拋出的異常不能比父類更寬廣。
(4) is-a:指繼承。
has-a:指類實例具有對另一個實例的引用。
(5) 對於繼承關係:當子類的對象來調用父類中的方法時,則執行的是父類只中原有的方法,
這和多態不一樣,如果子類覆蓋掉父類的這個方法時,則調用的是子類的這個方法。
3. 多態:
(1) 前提:把子類對象當成父類對象來看。
(2) 把子類對象當成父類對象來看時:只能調用父類中定義的屬性和方法。
(3) 把子類對象當成父類對象來看時:如果子類覆蓋了父類中的方法,則調用的
是子類覆蓋後的這個方法。
但是如果調用屬性時是調用父類的屬性而並非子類的,所以儘量不要定義
父子類同名的屬性。
(4) 把父類強制轉換成子類時,則調用的是子類中的方法。
4. 靜態方法不能叫"多態". 切記!
靜態方法不可被覆蓋,如果子類和父類有重名的靜態方法,雖然編譯通過,但並不能實現多態,所以不能
叫"覆蓋"。例如:Animal a = new Bird(); a.move();如果是"多態"的話應該輸出的結果爲,子類中的結果,
但是實際不是,它是調用的是父類中的方法。所以不能叫"覆蓋(多態)"。
1. 繼承:
(1)子類的構造方法一定會調用父類的構造方法。
(2)任何子類構造方法第一行肯定是this();或者super();兩個擇一。
this();調用本類的其它構造方法。(傳遞相應參數調用相應的方法)
super();調用父類的構造方法。
2. 覆蓋:
子類覆蓋父類前提:
(1) 同名,同參數列表,同返回類型。
(2) 子類覆蓋後的方法的訪問權限只能比父類相同或者更寬廣。
(3) 子類覆蓋後的方法拋出的異常不能比父類更寬廣。
(4) is-a:指繼承。
has-a:指類實例具有對另一個實例的引用。
(5) 對於繼承關係:當子類的對象來調用父類中的方法時,則執行的是父類只中原有的方法,
這和多態不一樣,如果子類覆蓋掉父類的這個方法時,則調用的是子類的這個方法。
3. 多態:
(1) 前提:把子類對象當成父類對象來看。
(2) 把子類對象當成父類對象來看時:只能調用父類中定義的屬性和方法。
(3) 把子類對象當成父類對象來看時:如果子類覆蓋了父類中的方法,則調用的
是子類覆蓋後的這個方法。
但是如果調用屬性時是調用父類的屬性而並非子類的,所以儘量不要定義
父子類同名的屬性。
(4) 把父類強制轉換成子類時,則調用的是子類中的方法。
4. 靜態方法不能叫"多態". 切記!
靜態方法不可被覆蓋,如果子類和父類有重名的靜態方法,雖然編譯通過,但並不能實現多態,所以不能
叫"覆蓋"。例如:Animal a = new Bird(); a.move();如果是"多態"的話應該輸出的結果爲,子類中的結果,
但是實際不是,它是調用的是父類中的方法。所以不能叫"覆蓋(多態)"。
Java代碼
多態:
Animal a = new Bird(); a客觀是鳥(客觀類型)
Bird b = (Bird)a ;
其中:Animal a,在編譯時a爲Animal。編譯類型叫"編譯時多態",主觀。
new Bird(),叫:"運行時多態",客觀。
Bird b = (Bird)a ;把父類強制轉換成子類。
if(a instanceof Animal) ----> 編譯類型
if(a instanceof Bird) -----> 客觀類型
if(b instanceof Animal) -----> 自動向上兼容
多態:
Animal a = new Bird(); a客觀是鳥(客觀類型)
Bird b = (Bird)a ;
其中:Animal a,在編譯時a爲Animal。編譯類型叫"編譯時多態",主觀。
new Bird(),叫:"運行時多態",客觀。
Bird b = (Bird)a ;把父類強制轉換成子類。
if(a instanceof Animal) ----> 編譯類型
if(a instanceof Bird) -----> 客觀類型
if(b instanceof Animal) -----> 自動向上兼容
Java代碼
this的用法:
this._ (區分局部變量與全局變量,有重名時用)
this(參數類表)
super的用法:
super._(區分子類與父類同名屬性,以後建議不要定義相同的同名屬性)
super(參數列表)
this的用法:
this._ (區分局部變量與全局變量,有重名時用)
this(參數類表)
super的用法:
super._(區分子類與父類同名屬性,以後建議不要定義相同的同名屬性)
super(參數列表)
Java代碼
寫一個類時,同時順手的要加上一個無參的構造方法,有其它類繼承它時,
加上super();但父類如果沒有無參的構造方法就會報錯。
寫一個類時,同時順手的要加上一個無參的構造方法,有其它類繼承它時,
系統會自動加上super();但父類如果沒有無參的構造方法就會報錯。
Java代碼
覆蓋(重寫)和重載的區別:
覆蓋:(1) 是父子類之間.
(2) 父子類同名,相同的參數列表,相同的返回類型。
(3) 子類訪問的權限比父類要高。
(4) 子類拋出的異常比父類小。
重載:(1) 多數針對一個類.
(2) 方法名相同,參數列表不同,與返回類型無關。
(3) 也可能出現在父子類中。
(4) 一般會想到構造函數,有無參的構造函數,一個參數的,兩個參數的。
覆蓋(重寫)和重載的區別:
覆蓋:(1) 是父子類之間.
(2) 父子類同名,相同的參數列表,相同的返回類型。
(3) 子類訪問的權限比父類要高。
(4) 子類拋出的異常比父類小。
重載:(1) 多數針對一個類.
(2) 方法名相同,參數列表不同,與返回類型無關。
(3) 也可能出現在父子類中。
(4) 一般會想到構造函數,有無參的構造函數,一個參數的,兩個參數的。
補充:
Java代碼
package com.ctit;
public class Test {
public static void main(String[] args){
A a = new B(); 這裏是把子類當成父類來看,則只能調用父類中定義的屬性和方法。
//a.hello(5); 如果子類覆蓋了父類中的方法,則調用的是子類覆蓋後的那個方法。
B b = (B)a; 這裏是把父類強轉成子類,這裏千萬不能寫成A a = new A();這樣的話運行時會報錯,只能是上面的那個A a = new B();
b.hello(4);強轉後調用的是子類中的方法(對覆蓋來說)
b.hello2();強轉後也可以調用父類中的方法
}
}
class A{
public void hello(int i){
System.out.println("A="+i);
}
public void hello2(){
System.out.println("hello2");
}
}
class B extends A{
public void hello(int j){
System.out.println("B="+j);
}
下面的這個方法不是覆蓋哦!要看好覆蓋的前提哦~!
public void hello(long l){
System.out.println("B2="+l);
}
}
|