Java — 面向對象

一、類和對象

簡介:類是對事物的一種描述,對象則為具體存在的事物。

類的定義:

public class 類名 {
    // 成員變數
    訪問修飾符 數據類型 變數名;
    …
    // 成員方法
    訪問修飾符 返回類型 方法名(參數列表) { 
        若干語句; 
        return 方法返回值; 
    }
    ...
}

創建對象:類名 對象名 = new 類名();

成員調用:對象名.成員變數;,對象名.成員方法(參數列表);

二、方法

定義:訪問修飾符 返回值類型 方法名(參數列表) { 方法邏輯; return 方法返回值 } 。

調用:方法名(參數列表);

分類:無參數無返回值、無參數有返回值、有參數無返回值、有參數有返回值。

傳值:

  1. 基本類型:調用方值的複製,雙方各自的後續修改互不影響。方法內部對參數變數做的任何操作都不會影響方法外部的變數。
  2. 引用類型:調用方的變數和接收方的參數變數,記憶體地址指向同一個對象。雙方任意一方修改該參數值都會影響對方。
  3. 可變參數:當方法的參數列表有兩個或多個參數時,可變參數需放在末尾。

進階:

  1. 類作為形參和返回值:方法的形參是類,需要該類的對象。方法的返回值是類,返回該類的對象;
  2. 抽象類作為形參和返回值:方法的形參是抽象類,需要該抽象類子類對象。方法的返回值是抽象類,返回該抽象類的子類對象;
  3. 介面作為形參和返回值:方法的形參是介面,需要該介面的實現類對象。方法的返回值是介面名,返回該類的實現類對象。

三、封裝

簡介:封裝是面向對象程式語言對客觀世界的模擬,客觀世界裡成員變數都隱藏在對象內部,外界無法直接操作。

原則:將類的某些資訊隱藏在類內部,不允許外部程式直接訪問,而是通過該類提供的方法來實現對隱藏資訊的操作和訪問。

實現:

  1. 使用 private 訪問修飾符將對象的屬性私有化;
  2. 創建公開的 get / set 方法用於對屬性的讀寫;
  3. 在 get / set 方法中對屬性的合法性進行判斷。

private 關鍵字:

  1. 是一個可以修飾成員資訊的許可權修飾符;
  2. 被其修飾的成員只能在本類中訪問,不能被其它類使用;
  3. 被其修飾的成員提供公共的 get / set 方法,供其它類使用。

this 關鍵字:

  1. 指向當前對象的引用(誰調用我就代表誰);
  2. 通過 this.成員變數 | 成員方法(參數列表) | (參數列表) 來訪問本類的成員變數、方法,構造方法;
  3. 使用時必須在方法體第一行,不能在靜態方法中使用。

構造方法:

  1. 是一種特殊的方法,用於創建對象並完成對象的初始化;
  2. 格式為 public class 類名 { 修飾符 類名(參數列表) };
  3. 沒有自定義構造方法,系統會提供一個默認的無參構造方法,若自定義了構造方法,系統不再提供默認的無參構造方法。

四、繼承

由來:多個類中存在相同屬性和行為時,將這些相同內容抽取到一個公共類中,則其它類中無需再定義這些屬性和行為,只需繼承公共類即可。

定義:就是子類繼承父類的屬性和行為,使得子類對象具有與父類對象相同的屬性和行為,且子類可直接訪問父類的非私有屬性和行為。

格式:public class 子類名 extends 父類名 {...} 。

好處:提高程式碼的復用性,類與類之間產生了關係,是多態的前提。

特點:只支援單繼承,不支援多繼承,但支援多層繼承。

方法重寫:

  1. 子類必須有和父類相同的方法名、參數列表和返回類型,且該父類方法沒有被 final 或 static 修飾;
  2. 子類的重寫方法其訪問修飾符的限定範圍應大於等於父類方法,即 public > protected > default ;
  3. 子類不能重寫父類構造方法,只能通過 super(參數列表) 調用。

訪問修飾符:

  1. public(公共的):同類、同包、不同包的子類、不同包的非子類,均可訪問;
  2. protected(受保護的):同類、同包、不同包的子類,均可訪問;
  3. default(默認的):同類、同包,均可訪問;
  4. private(私有的):同類,才可訪問。

super 關鍵字:

  1. 代表父類存儲空間的標識,可理解為父類對象引用;
  2. 子類通過 super.成員變數 | 成員方法(參數列表) | (參數列表) 來訪問父類的成員變數、方法,構造方法;
  3. 使用時必須在方法體第一行。

super 和 this 的區別:

  1. 父類空間優先於子類對象產生,在每次創建子類對象時,先初始化父類空間再創建其子類對象本身。
    目的在於子類對象中包含了其對應的父類空間便可包含其父類成員。
  2. super.成員變數 | 成員方法(參數列表) | (參數列表) 訪問的是父類的成員變數、方法,構造方法;
  3. this.成員變數 | 成員方法(參數列表) | (參數列表) 訪問的是本類的成員變數、方法,構造方法;
  4. super 和 this 不能同時使用,只能存在一個,並且都在方法體第一行。

成員訪問特點:

  1. 變數:子類局部範圍找 > 子類成員範圍找 > 父類成員範圍找 > 若都沒有則報錯、不考慮父類的父類。
  2. 方法:子類成員範圍找 > 父類成員範圍找 > 若都沒有則報錯、不考慮父類的父類。

五、多態

簡介:同一對象在不同時刻表現出不同的形態。

特點:相同的消息給予不同的對象會引發不同的動態,也就是允許不同類的對象對同一消息做出不同的響應。

實現:滿足繼承(實現)關係、要有方法重寫、父類引用指向子類對象。

訪問:成員變數(編譯看左邊,執行看左邊),成員方法(編譯看左邊,執行看右邊)。

好處:定義方法時,使用父類型作為參數,將來調用時使用具體的子類型參與操作。

弊端:不能使用子類的特有方法。

轉型:

  1. 向上轉型:又稱自動轉型、隱式轉型,從子到父,子類對象賦值給父類對象,就是說父類引用指向子類實例;
    格式:父類名 對象名 = new 子類名(); ,此時該對象不能調用子類的特有方法。
  2. 向下轉型:又稱強制轉型,從父到子,父類對象賦值給子類對象,就是說子類引用指向父類實例;
    格式:子類名 對象名 = (子類名) 父類實例; ,此時該對象可以調用子類的特有方法,解決了多態的弊端。
  3. instanceof:返回一個布爾值來確認某個對象,是否是某個特定類或該特定類子類的一個實例,就是說左邊的對象是不是右邊類的實例;
    格式:對象名 instanceof 類型 ,類型可以為類或介面。

六、final

簡介:final 關鍵字是最終的意思,可以修飾類、成員方法、成員變數。

修飾類:

  1. 被 final 修飾的類叫做最終類,不能被其它類繼承;
  2. 類中的所有方法都被隱式設置為 final ,但類中成員變數可以被定義為 final 或非 final ;
  3. 格式:public final class 類名 {...} 。

修飾方法:

  1. 被 final 修飾的方法叫做最終方法,不能被子類重寫;
  2. 格式:訪問修飾符 final 返回值類型 方法名(參數列表) {...} 。

修飾變數:

  1. 被 final 修飾的變數叫做常量,名稱大寫;
  2. 成員變數具有默認值,被 final 修飾之後不再有默認值,需手動賦值;
  3. 局部變數一次賦值終生不變;
  4. 格式:訪問修飾符 final 數據類型 變數名(大寫) = 手動賦值 。

七、static

簡介:static 關鍵字是靜態的意思,訪問修飾成員方法、成員變數。

修飾方法:

  1. 被 static 修飾的方法叫做靜態方法,也稱為類方法,可通過 類名.方法名 直接調用;
  2. 靜態成員方法只能訪問靜態的成員變數和方法;
  3. 非靜態成員方法可以訪問非靜態的成員變數和方法,也可以訪問靜態成員變數和方法。

修飾變數:

  1. 靜態變數:被 static 修飾的成員變數叫做靜態變數,也稱為類變數,靜態變數屬於這個類,而不是屬於這個類的對象;
    靜態變數通過 類名.變數名 直接調用。
  2. 實例變數:沒被 static 修飾的成員變數叫做實例變數,實例變數屬於這個類的實例對象;
    實例變數必須先 new 一個對象之後,通過 對象名.變數名 調用。

八、抽象類

簡介:在做子類共同功能抽取時,有些方法在父類中並沒有具體的體現,此時就需要抽象類。

格式:public abstract class 類名 {...} 。

特點:

  1. 抽象類和抽象方法必須使用 abstract 關鍵字修飾;
  2. 抽象類中不一定有抽象方法,但有抽象方法的類一定是抽象類;
  3. 抽象方法不能實例化,要想實例化可參照多態的方式,通過子類對象實例化,這叫做抽象類多態;
  4. 抽象類的子類,要麼重寫抽象類中的所有抽象方法,要麼子類也是抽象類。

內部:

  1. 成員變數:既可以是變數也可以是常量;
  2. 成員方法:既可以是普通方法也可以是抽象方法;
  3. 構造方法:無參有參構造方法。

注意:

  1. 與 abstract 不能共存的關鍵字:final 、private 、static ;
  2. final:被 final 修飾的類不能有子類,而被 abstract 修飾的類一定是個父類;
  3. private:抽象類中私有的抽象方法,不被子類所知就無法重寫,而抽象方法必須被重寫。
  4. static:若 static 可以修飾抽象方法,則不用 new 對象,直接類名調用即可,此時抽象方法沒有意義。

九、介面

簡介:介面就是一種公共的規範標準,只要符合規範標準,大家都可以通用。Java 中的介面更多的體現在對行為的抽象。

格式:public interface 介面名 {...} 。

特點:

  1. 介面用 interface 關鍵字修飾;
  2. 類實現介面用 implements 表示,例:public class 類名 implements 介面名 {...} ;
  3. 介面不能實例化,要想實例化可參照多態的方式,通過子類對象實例化,這叫做介面多態;
  4. 介面的子類要麼重寫介面中所有抽象方法,要麼子類也是抽象類。

內部:

  1. 成員變數:只能是常量,默認修飾符:public static final ;
  2. 成員方法:只能是抽象方法,默認修飾符:public abstract ;
  3. 構造方法:沒有,介面主要是擴展功能而沒有具體存在的。

抽象類與介面的區別:

  1. 成員區別:抽象類有變數、常量、構造方法、普通方法、抽象方法,介面只有常量、抽象方法。
  2. 關係區別:
    1. 類與類的關係:繼承關係,只能單繼承,支援多層繼承;
    2. 類與介面的關係:實現關係,可以單實現,也支援多實現,還可以繼承一個類的同時實現多個介面;
    3. 介面與介面的關係:繼承關係,可以單繼承,也支援多繼承。
  3. 設計理念:
    1. 抽象類:對類抽象,包括屬性和行為;
    2. 介面:對行為抽象,主要對行為。

新特性:JDK8 之前,介面只有常量以及抽象方法。JDK8 時,介面增加了默認方法和靜態方法。JDK9 時,介面增加了私有方法。

默認方法:

  1. 格式:default 返回值類型 方法名(參數列表) {...} ;
  2. 注意:默認方法不是抽象方法,也可以重寫,重寫時去掉 default 關鍵字;
  3. 作用:對介面的升級不會影響到現有程式碼。

靜態方法:

  1. 格式:static 返回值類型 方法名(參數列表) {...} ;
  2. 注意:靜態方法只能通過介面名調用,不能通過實現類名或對象名調用。

私有方法:

  1. 格式1:private 返回值類型 方法名(參數列表) {...} ;
  2. 格式2:private static 返回值類型 方法名(參數列表) {...} ;
  3. 注意:默認方法可以調用私有的靜態方法和非靜態方法,靜態方法只能調用私有的靜態方法;
  4. 作用:提取默認方法和靜態方法中相同的程式碼,提高程式碼的復用性。

十、內部類

簡介:就是在一個類中定義一個類,例:在類 A 的內部定義類 B,類 B 就是內部類。

格式:public class 類名 { 訪問修飾符 class 類名 } 。

特點:內部類可以直接訪問外部類的成員(包括私有),外部類要訪問內部類的成員必須創建對象。

分類:

  1. 成員內部類:在類的成員位置,外界訪問通過 外部類名.內部類名 對象名 = new 外部類名().new 內部類名(); ;
    但一般都是私有化的,不會讓外界直接訪問,而是通過在外部類中定義一個方法,在該方法中實例化內部類,調用內部類方法;
    最終外界通過外部類的這個方法達到訪問內部類的效果。
  2. 局部內部類:在類的方法體中,外界無法直接訪問,需在方法體中創建對象並使用,最終外界通過該方法達到訪問局部內部類的效果;
  3. 匿名內部類:局部內部類的簡寫形式,前提是繼承類或實現介面,格式:new 類名() | 介面名() { 重寫方法 } ;
    本質上是一個繼承了該類或實現了該介面的子類匿名對象,就是說該類沒有聲名對象名。
Tags: