如果要在程式當中設計「書本」跟「報紙」的類別,兩者具有共通的特性,不外是紙張、文字、圖片等,此時物件導向提供一個避免重複程式碼的方法,也就是利用子類別 (subclass) 去繼承 (inherit) 父類別 (superclass) ,這樣一來,共通的程式碼都可以放在父類別之中,無須每一個類別都重複相同的程式碼。
「繼承」是物件導向程式設計中一個重要也是核心的觀念,動詞原文為 inherit 。雖然 inherit 在英文的意思泛指從什麼得到什麼,用作中文「繼承」說得通,也能用作「遺傳」。然而中文的「繼承」隱含某物不再,另物將起的意思,譬如「我繼承某某的精神」,雖然某某不見得已死,未來將要付出努力的卻是我而非某某。因而這裡的意思中文用「遺傳」比較恰當,子代會從親代遺傳某些生物特性,子代與親代也會並存一段時間,這就沒有某物不再的意含了。然而這裡我們仍沿用程式設計常用的「繼承」一詞,但仍提出意見以免讀者混淆。
我們以下用個簡單的範例說明繼承的使用
class Animal { int age; int weight; void speak() { System.out.println("哈囉,我已經" + age + "歲,有" + weight + "公斤重"); } } class Elephant extends Animal { String name; void speak() { System.out.println("我的名字是" + name + "已經" + age + "歲"); } } class JungleDemo1 { public static void main(String[] args) { Animal puppy1 = new Animal(); puppy1.age = 12; puppy1.weight = 25; puppy1.speak(); Elephant puppy2 = new Elephant(); puppy2.age = 8; puppy2.weight = 1200; puppy2.name = "大象"; puppy2.speak(); } } /* 《程式語言教學誌》的範例程式 http://pydoing.blogspot.com/ 檔名:JungleDemo1.java 功能:示範物件導向的基本觀念 作者:張凱慶 時間:西元 2010 年 10 月 */
編譯後執行,結果如下
首先, Animal 為我們設計的父類別,因此每一個以 Animal 建構的物件,或是繼承自 Animal 的物件都會有整數 int 型態的 age 及 weight 屬性 (field) ,以及 speak() 方法 (method) 。
Elephant 為我們設計的子類別,注意第 10 行
class Elephant extends Animal {
關鍵字 extends 標示 Elephant 繼承自 Animal ,注意, Java 的子類別只能繼承自單一父類別,但可以實作多個不同介面 (interface) ,這所謂的介面像是共通的規格,我們往後才會詳加介紹。
我們添加了 name 屬性,這是 Elephant 所專有的,父類別 Animal 並不具有 name ,子類別 Elephant 的屬性包含 Animal 的 age 及 weight 。 extends 過父類別的東西,子類別就不必贅述一次,也就是無須寫重複的 age 及 weight 。
留意父類別 Animal 有個 speak() 方法,子類別也有個 speak() 方法,繼承的規則是父類別有的,子類別也都會有,但是子類別可以增加專屬的屬性或方法,這裡卻出現相同名稱的方法,這裡是子類別改寫 (override) 父類別原先設計的方法。若是沒有改寫,子類別會一字不改的延續使用父類別的方法,改寫的原因通常是子類別具有其他特性,如此例中 Elephant 多了 name 屬性。
第 21 行到第 30 行
Animal puppy1 = new Animal(); puppy1.age = 12; puppy1.weight = 25; puppy1.speak(); Elephant puppy2 = new Elephant(); puppy2.age = 8; puppy2.weight = 1200; puppy2.name = "大象"; puppy2.speak();
第 21 行宣告同時建立 Animal 型態的 puppy1 ,其後第 22 行及第 23 行利用句點運算子 (dot operator) 設定屬性 age 及 weight 的值,最後在第 24 行呼叫 speak() 方法。
第 26 行則是宣告同時建立 Elephant 型態的 puppy2 ,其後的過程類似。注意,這裡是簡單說明 Java 程式可以這樣寫,但沒有用到封裝 (encapsulation) 的特性,會使資料在程式中任意被存取,我們稍後會繼續解釋如何進行封裝,達到良好的資訊隱藏 (information hiding) 。
由於設計類別就等於設計型態, Java 程式由一堆以類別為藍本的物件組成,因此具有非常多不同的型態,如果有效利用各種型態,就是物件導向另一個重要觀念,也就是多型 (polymorphism) 。關於多型,我們稍後會詳細說明。
中英文術語對照 | |
---|---|
物件導向程式設計 | object-oriented programming |
物件 | object |
類別 | class |
型態 | type |
子類別 | subclass |
繼承 | inherit |
父類別 | superclass |
屬性 | field |
方法 | method |
介面 | interface |
改寫 | override |
句點運算子 | dot operator |
封裝 | encapsulation |
資訊隱藏 | information hiding |
多型 | polymorphism |
參考資料
http://download.oracle.com/javase/tutorial/java/IandI/subclasses.html
http://download.oracle.com/javase/tutorial/java/IandI/override.html
http://download.oracle.com/javase/tutorial/java/IandI/hidevariables.html
http://java.sun.com/docs/books/jls/third_edition/html/classes.html
http://download.oracle.com/javase/tutorial/java/IandI/subclasses.html
http://download.oracle.com/javase/tutorial/java/IandI/override.html
http://download.oracle.com/javase/tutorial/java/IandI/hidevariables.html
http://java.sun.com/docs/books/jls/third_edition/html/classes.html
沒有留言:
張貼留言