物件導向中的抽象類別與抽象方法

UML class pet

在物件導向程式設計中,有關抽象類別的描述下列何者錯誤?
(A)抽象類別可定義抽象方法 (B)抽象類別可被一般類別直接繼承 (C)可生成抽象類別的物件 (D)抽象類別可實作一般方法

答案:(C)

這是112 年公務人員初等考考試試題資料處理大意第5題,有點好笑,我在這幾年的C#程式設計中,抽象類別不曾有用過的跡象,但是在2009年我曾寫了抽象類別(Abstract class)一文,一看就知道那時是為了準備昇陽認證Java程式員(英文:Sun Certified Programmer for Java,SCJP),這看起來是最基本的概念。

後來又在50個 C# 工作面試常見問題看到C# 介面跟抽象類別的差異,這應該是很重要啊,但是為什麼我的編碼生涯中卻是那麼地少用?

後來在HackMD找到了抽象類別與抽象方法 & 介面(interface)這篇筆記,轉貼一段內容於下:

抽象方法(abstraction method):

只有定義方法(成員函數)的「呼叫方式」,而沒有定義方法實際上到底要做什麼事情的程式碼。也就是說,抽象方法只有方法的頭(名稱和小括號()區塊),而沒有方法的身體(沒有大括號{ }區塊)。
abstract class Animal { // 抽象類別
    class bird (); // 這邊沒有身體(也就是沒有方法 method 的實作)
}

特別注意的是,抽象方法只能定義在抽象類別的{ }之中,否則會編譯錯誤。

abstract class Animal {
    class bird () {
        ...
    } // <- error
}

Abstract method 則是一種只有宣告,而沒有實作內容的一種特殊 method。Abstract method 主要的目標是預先宣告 method,但是把實作的工作交給繼承的類別來做。透過使用 abstract method,就可以讓衍生類別具有共同行為,但是實際的做法則由各個類別自訂。

抽象類別(abstraction class):

類別裡面包含了「至少一個」抽象方法,就稱為抽象類別。如果一個類別中包含了至少一個抽象方法,則該類別就必須被宣告成「抽象類別」(加上abstract關鍵字)例如:
「public abstract class Animal{ … … … }」。

這樣的定義讀者應該還是看不太懂,以實例來說明。如果有一個表格,上面寫著「姓名:」,你就明確知道這裡要填上你的名字。「姓名:」就類似於「抽象方法」,因為它只定義了呼叫方式,但沒有實際可作用的程式碼。

而「抽象類別」就是指裡面含有「至少一個」抽象方法的類別,例如機場海關的入境表格就是一個抽象類別,表格的格式雖然都有清楚的標示和規範,但實際的內容全部都是空白的,要旅客自己填寫。

入境表格「強迫」每個旅客一定要複寫(override)掉抽象方法,也就是要把入境表格的抽象方法給填上每個旅客自己的資料,表格才會發揮效用。而旅客填表的動作,就稱為「實作」(implement),也就是字面上的意思:把實際的內容(程式碼)給實際做出來。

為什麼要這麼麻煩?舉這個入境表格的例子,大家應該就立刻明白了。由於每個旅客的個人資料都是不同的,入境表格只能預先做好格式,但沒辦法幫大家填表,必須要透過每個物件自行以複寫來實作,這張表格才能發揮效用。

抽象類別或抽象方法在大型、多人協作的工作專案中比較有用,小型程式直接實作就好了。抽象類別或抽象方法可以幫助我們規劃程式的架構,讓多人合作的大型軟體專案或軟體工程變得更有架構和規劃,更有系統性,是屬於「架構設計」的功能。抽象類別或抽象方法可以方便上層的領導人員規劃程式架構,指派工作給各個軟體工程師去實作出來,並且可以更明確的劃分責任範圍,讓除錯與維護更有效率(例如主管罵說:這個方法(method)的實作亂七八糟,是誰寫的code?給我重寫)。

就好像公司創立初期業務量少,老闆一人就可以實作公司所有的大小事務。不過當公司發展到一定的規模時,老闆就必須制定良好的公司組織結構和章程規範、制定工作目標(抽象),並雇用員工來實踐所下達的任務(實作),而每個員工各司其職,做不一樣的事情,最後整合起來完成目標。

由於抽象類別包含了至少一個抽象方法,抽象方法沒有實作的程式碼,因此無法直接被實體化,所以抽象類別(abstract class)必須先以「繼承」的方式轉為一般的類別(class),然後在(一般的)類別中把抽象方法給實作出來,之後再實體化產生物件,讓物件使用(具體的)方法。

–>原來是我工作的模式算是一人公司,我寫的都算是小型程式,所以我通常都只有實作的份,要做這種大型專案,我看是不大有機會。

感謝你看到這裡,很快就可以離開了,但最好的獎勵行動就是按一下幫我分享或留言,感恩喔~

點我分享到Facebook

發佈留言

發佈留言必須填寫的電子郵件地址不會公開。 必填欄位標示為 *