Java學習筆記(十一)面向對象---多態

来源:https://www.cnblogs.com/liyuxin2/archive/2020/02/15/12313781.html
-Advertisement-
Play Games

多態的體現 父類的引用指向了自己的子類對象。 父類的引用也可以接受自己的子類對象。 代碼體現 運行結果 多態的前提 必須是類與類之間有關係。要麼是繼承關係,要麼實現。 存在覆寫關係。 多態利弊 利處 多態的出現大大地提高了程式的拓展性。 弊端 提高了拓展性,但是只能使用父類的引用訪問父類中的成員,不 ...


多態的體現

父類的引用指向了自己的子類對象。
父類的引用也可以接受自己的子類對象。

代碼體現

abstract class Animal {
    public abstract void eat();
}
class Cat extends Animal {
    @Override
    public void eat() {
        System.out.println("eat fish");
    }
}
class Dog extends Animal {
    @Override
    public void eat() {
        System.out.println("eat bone");
    }
}
class Monkey extends Animal {
    @Override
    public void eat() {
        System.out.println("eat banana");
    }
}
public class Demo {
    public static void main(String[] args) {
        /*
        Animal c = new Cat();
        function(c);
         */
        function(new Cat());
        /*
        Animal d = new Dog();
        function(d);
        */
        function(new Dog());
        /*
        Animal m = new Monkey();
        function(m);
        */
        function(new Monkey());
    }
    public static void function(Animal a) {
        a.eat();
     }
}

運行結果

eat fish
eat bone
eat banana

多態的前提

必須是類與類之間有關係。要麼是繼承關係,要麼實現。
存在覆寫關係。

多態利弊

利處

多態的出現大大地提高了程式的拓展性。

弊端

提高了拓展性,但是只能使用父類的引用訪問父類中的成員,不能預先訪問子類的成員(因為子類這時還不存在)。

多態-示例

abstract class Student {
    public void eat() {
        System.out.println("eat rice");
    }
    public abstract void study();
}
class StudentToDo {
    public void Do(Student s) {
        s.eat();
        s.study();
    }
}
class StudentClass1 extends Student {
    @Override
    public void eat() {
        System.out.println("eat steak");
    }
    @Override
    public void study() {
        System.out.println("study English");
    }
}
class StudentClass2 extends Student {
    @Override
    public void study() {
        System.out.println("study Chinese");
    }
}
class StudentClass3 extends Student {
    @Override
    public void study() {
        System.out.println("study Japanese");
    }
}
public class Demo2 {
    public static void main(String[] args) {
        StudentToDo std =  new StudentToDo();
        std.Do(new StudentClass1());
        std.Do(new StudentClass2());
        std.Do(new StudentClass3());
    }
}

運行結果:

eat steak
study English
eat rice
study Chinese
eat rice
study Japanese

多態的出現 代碼中的特點(多態使用的註意事項)

多態中成員函數的特點

在編譯時期,參閱引用類型變數所屬的類中是否有調用的方法,如果有編譯通過,如果沒有編譯失敗。
在運行時期,參閱對象所屬的類中是否有調用的方法。
簡單總結:成員函數在多態調用時,編譯看左邊,運行看右邊。

class Fu {
    void method1() {
        System.out.println("Fu_Method_1");
    }
    void method2() {
        System.out.println("Fu_Method_2");
    }
}
class Zi extends Fu {
    @Override
    void method1() {
        System.out.println("Zi_Method_1");
    }
    void method3() {
        System.out.println("Zi_Method_3");
    }
}
public class Demo3 {
    public static void main(String[] args) {
        Fu f =new Zi();
        f.method1();
        f.method2();
        //f.method3(); 對於引用類型f所屬的類Fu中沒有method3()方法,所以編譯會不通過。
    }
}

運行結果:

Zi_Method_1
Fu_Method_2

多態中成員變數的特點

無論編譯還是運行,都參考左邊(引用型變數所屬的類)

class Fu {
    int num = 1;
}
class Zi extends Fu {
    int num = 2;
}
public class Demo4 {
    public static void main(String[] args) {
        Fu f = new Zi();
        System.out.println(f.num);   //參考左邊
        Zi z= new Zi();
        System.out.println(z.num);
    }
}

運行結果:

1
2

多態中靜態成員函數(變數)的特點

無論編譯還是運行,都參考左邊。
靜態類型,靜態綁定。
非靜態類型,動態綁定。

class Fu {
    static void method1() {
        System.out.println("Fu_Method_1");
    }
}
class Zi extends Fu {
    static void method1() {
        System.out.println("Zi_Method_1");
    }
}
public class Demo5 {
    public static void main(String[] args) {
        Fu f = new Zi();
        f.method1();
        Zi z = new Zi();
        z.method1();
    }
}

運行結果:

Fu_Method_1
Zi_Method_1

多態-轉型

abstract class Animal {
    public abstract void eat();
}
class Cat extends Animal {
    @Override
    public void eat() {
        System.out.println("eat fish");
    }
    public void CatchMouse() {
        System.out.println("CatchMouse");
    }
}
class Dog extends Animal {
    @Override
    public void eat() {
        System.out.println("eat bone");
    }
    public void GuardHouse() {
        System.out.println("GuardHouse");
    }
}
class Monkey extends Animal {
    @Override
    public void eat() {
        System.out.println("eat banana");
    }
    public void PlayBall() {
        System.out.println("Play Ball");
    }
}
public class Demo1 {
    public static void main(String[] args) {
        function(new Cat());
        function(new Dog());
        function(new Monkey());
    }
    public static void function(Animal a) {
        a.eat();
        if (a instanceof Cat) { //instanceof關鍵字用於判斷所屬類型
            Cat c = (Cat)a;     //向下轉型
            c.CatchMouse();
        } else if (a instanceof Dog) {
            Dog d = (Dog)a;     //向下轉型
            d.GuardHouse();
        } else {
            Monkey m = (Monkey)a;//向下轉型
            m.PlayBall();
        }
    }
}

運行結果:

eat fish
CatchMouse
eat bone
GuardHouse
eat banana
Play Ball

多態的應用

以電腦主板為例的示例
分析電腦主板要考慮到拓展性,使用了pci介面,板卡(音效卡,網卡等)和主板都遵循pci介面。

interface Pci {
    public void open();
    public void close();
}

class MainBoard {
    public void run() {
        System.out.println("Main Board run");
    }
    public void usePci(Pci p){ //介面類型指向自己的子類對象
        if(p != null){    //加入判斷防止空指針
        p.open();
        p.close();
        }
    }
}
class Netcard implements Pci {
    @Override
    public void open() {
        System.out.println("Netcard open");
    }

    @Override
    public void close() {
        System.out.println("Netcard close");
    }
}
class Soundcard implements Pci {
    @Override
    public void open() {
        System.out.println("Soundcard open");
    }

    @Override
    public void close() {
        System.out.println("Soundcard close");
    }
}
public class Demo6 {
    public static void main(String[] args) {
        MainBoard mb = new MainBoard();
        mb.run();
        mb.usePci(null);
        mb.usePci(new Netcard());
        mb.usePci(new Soundcard());
    }
}

運行結果

Main Board run
Netcard open
Netcard close
Soundcard open
Soundcard close

您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 楔子 假如我現在有一個列表l=['a','b','c','d','e'],我想取列表中的內容,有幾種方式? 首先,我可以通過索引取值l[0],其次我們是不是還可以用for迴圈來取值呀? 你有沒有仔細思考過,用索引取值和for迴圈取值是有著微妙區別的。 如果用索引取值,你可以取到任意位置的值,前提是你 ...
  • 楔子 作為一個會寫函數的python開發,我們從今天開始要去公司上班了。寫了一個函數,就交給其他開發用了。 def func1(): print('in func1') 季度末,公司的領導要給大家發績效獎金了,就提議對這段日子所有人開發的成果進行審核,審核的標準是什麼呢?就是統計每個函數的執行時間。 ...
  • 楔子 假如有一個函數,實現返回兩個數中的較大值: def my_max(x,y): m = x if x>y else y return mbigger = my_max(10,20)print(bigger) 之前是不是我告訴你們要把結果return回來你們就照做了?可是你們有沒有想過,我們為什麼 ...
  • 好久時間沒有做Django的項目了,今天創建項目竟然報Non-zero exit code(1)錯誤 查明原因是因為pip不是最新版本,需要執行以下命令:python -m pip install --upgrade pip 但還是沒有成功,提示超時,估計源有問題 使用豆瓣源進行安裝,問題解決了 命 ...
  • 前言最近由於疫情被困在家,於是準備每天看點專業知識,準備寫成博客,不定期發佈。博客大概會寫5~7篇,主要是“解剖”一些深度學習的底層技術。關於深度學習,電腦專業的人多少都會瞭解,知道Conv\Pool的過程,也看過論文,做過實驗或是解決方案。在寫的各種捲積網路 時候,有沒有問問自己:這些網路到底是... ...
  • 為什麼要用函數 現在python屆發生了一個大事件,len方法突然不能直接用了。。。 然後現在有一個需求,讓你計算'hello world'的長度,你怎麼計算? 這個需求對於現在的你其實不難,我們一起來寫一下。 s1 = "hello world" length = 0 for i in s1: l ...
  • 慕課網-悟空-玩轉Java併發工具,精通JUC,成為併發多面手-筆記 微雲:https://share.weiyun.com/81aa12bb98016e200add31fb8e191cdf百度網盤:鏈接:https://pan.baidu.com/s/1IiClTkQwFJgBL2NqlptKbA ...
  • 一、前言 從學單片機開始鼓搗C語言,到現在為了學CV鼓搗Python,期間在CSDN、簡書、博客園和github這些地方得到了很多幫助,所以也想把自己做的一些小東西分享給大家,希望能幫助到別人。記錄人生的第一篇博客,mark。 二、圖像檢測步驟 1. 讀取兩張圖片 第一張是需要檢測的小物體,第二章圖 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...