Java面向對象--多態

什麼是多態

多態,顧名思義,就是多種形態;是同一個行爲具有多個不同表現形式或形態的能力。如學生是人的一種,則一個具體的同學小明既是學生也是人,即出現兩種形態

多態的體現格式

父類名稱 變量名 = new 子類對象;
接口名稱 對象名 = new 實現類名稱();

多態存在的三個必要條件

多態的前提是類與類之間存在關係,要麼繼承、要麼實現或方法存在覆蓋
1、繼承:多態中必須存在有繼承關係的子類和父類
2、重寫:子類對父類中某些方法進行重新定義,在調用這些方法時就會調用子類的方法
3、父類引用指向子類對象(向上轉型):多態中需要將子類的引用賦給父類對象,只有這樣該引用才能夠具備技能調用父類的方法和子類的方法

例子

基於繼承實現的多態

class Animal {
    private String name;
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
    public Animal(){
    }
    public void breathe(){
        System.out.println("呼吸");
    }
    /**
     * 重寫Object類toString()
     */
    public String toString(){
        return null;
    }
}

class Rabbit extends Animal{
    public Rabbit(){
        setName("兔子");
    }
    /**
     * 重寫父類方法,實現多態
     */
    public void breathe(){
        System.out.println(getName()+"呼吸");
    }
    public String toString(){
        return "Animal:" + getName();
    }
}
class Cat extends Animal{
    public Cat(){
        setName("Cat");
    }
    /**
     * 重寫父類方法,實現多態
     */
    public void breathe(){
        System.out.println(getName()+"呼吸");
    }
    public String toString(){
        return "Animal:" + getName();
    }
}
public class Test {
    public static void main(String[] args) {
        Animal rabbit = new Rabbit();
        Animal cat = new Cat();
        rabbit.breathe();
        cat.breathe();
        Rabbit rabbit1 = new Rabbit();
        Cat cat1 = new Cat();
        rabbit1.breathe();
        cat1.breathe();
    }
}

基於接口實現的多態

interface Animal {
    public void eat();
    public void activity();
}
class Rabbit implements Animal{

    @Override
    public void eat() {
        System.out.println("喫草");
    }

    @Override
    public void activity() {
        System.out.println("跳");
    }

    public static void main(String[] args) {
        Animal animal = new Rabbit();
        animal.eat();
        animal.activity();
        Rabbit rabbit = new Rabbit();
        rabbit.eat();
        rabbit.activity();
    }
}

多態中成員的特點

引用變量在編譯階段只能調用編譯時類型所具有的方法,但運行時則執行他運行時類型所具有的方法

class Animal{
    public int month = 1;
    
    public void eat(){
        System.out.println("喫東西");
    }
}
class Dog extends Animal{
    public int month = 2;

    public void eat() {
        System.out.println("小狗喫肉");
    }

    public void sleep() {
        System.out.println("小狗睡覺");
    }
}
class Cat extends Animal{
    public int month = 3;

    public void eat() {
        System.out.println("小貓喫魚");
    }
}
public class Test {
    public static void main(String[] args){
        Animal a = new Dog();
        Animal b = new Cat();
        a.eat();
        System.out.println(a.month);
        //下面代碼編譯時會出錯
        //a.sleep();
        b.eat();
        System.out.println(b.month);
    }
}

多態中成員函數的特點

在編譯時期,參考引用型變量所屬的類中是否有調用方法,如果有,編譯通過,否則編譯失敗
在運行時期,參考對象所屬的類中是否有調用的方法
也就是編譯看左邊,運行看右邊

多態中成員變量的特點

編譯和運行都參考左邊(引用型變量所屬的類)

多態中靜態成員函數的特點

編譯和運行都參考左邊

多態中引用類型轉換

向上轉型: 多態本身就是向上轉型過的過程

使用格式:父類類型 變量名=new 子類類型();
適用場景:當不需要面對子類類型時,通過提高擴展性,或者使用父類的功能就能完成相應的操作

Animal animal = new Dog();

向下轉型: 父類類型向子類類型向下轉換的過程,這個過程是強制的。 一個已經向上轉型的子類對象,將父類引用轉爲子類引用,可以使用強制類型轉換的格式,便是向下轉型

使用格式:子類類型 變量名 = (子類類型) 父類變量名;
含義:將父類對象還原成爲本來的子類對象

Dog dog = (Dog) animal;

注意:

必須保證對象創建的時候就是轉型後的對象,才能向下轉型。否則運行時,報出了 ClassCastException(類型轉換異常)

多態的優點與弊端

優點

1、消除類型之間的耦合關係
2、可替換性
3、可擴充性
4、接口性
5、靈活性
6、簡化性

弊端

只能使用父類的引用訪問父類中的成員

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章