抽象類和接口的區別

語法上面的就不用說了, 木球意思,

1、計層面上的區別

抽象類是對一種事物的抽象,而接口是對行爲的抽象。抽象類是對整個類整體進行抽象,包括屬性、行爲,但是接口卻是對類局部(行爲)進行抽象.

舉個例子;

  比如 飛機和鳥 是不同類的事物,但他們都有一個共性,那就是飛。那麼在設計的時候,可以將飛機設爲一個類Plane,將鳥設計爲一個類Bird,

但不能將飛行設計爲一個類,因爲是一個行爲特性,並不是對一類事物的抽象描述,此時可以將飛行設計爲一個接口Fly,包含方法fly( ),然後Plane,

Bird 實現這個接口,至於不同種類的飛機,比如戰鬥機、民用飛機等直接繼承Pane即可,對於鳥也是類似的,不同種類的鳥直接繼承Bird類即可,

從上面可以看出,接口是 “是不是”的關係,而是“有沒有”的關係

  如果一個類繼承了某個抽象類,則子類必定是抽象類的種類,而接口實現則是有沒有、具備不具備的關係,比如鳥是否能飛(或者是否具備飛行這個特點),能飛行則可以實現這個接口,不能飛行就不實現這個接口。 

2、設計層面不同

抽象類作爲很多子類的父類,它是一種模板式設計。而接口是一種行爲規範,是一種輻射式設計,什麼是模板式設計?最簡單例子,大家都用過ppt裏面的模板,如果用模板A設計了ppt B和ppt C,ppt B和ppt C公共的部分就是模板A了,如果它們的公共部分需要改動,則只需要改動模板A就可以了,不需要重新對ppt B和ppt C進行改動。而輻射式設計,比如某個電梯都裝了某種報警器,一旦要更新報警器,就必須全部更新。也就是說對於抽象類,如果需要添加新的方法,可以直接在抽象類中添加具體的實現,子類可以不進行變更;而對於接口則不行,如果接口進行了變更,則所有實現這個接口的類都必須進行相應的改動。

  下面看一個網上流傳最廣泛的例子:門和警報的例子:門都有open( )和close( )兩個動作,此時我們可以定義通過抽象類和接口來定義這個抽象概念:

  

abstract class Door {
    public abstract void open();
    public abstract void close();
}
或者

interface Door {
    public abstract void open();
    public abstract void close();
}

但是現在如果我們需要門具有報警alarm( )的功能,那麼該如何實現?下面提供兩種思路:

1)將這三個功能都放在抽象類裏面,但是這樣一來所有繼承於這個抽象類的子類都具備了報警功能,但是有的門並不一定具備報警功能;

2)將這三個功能都放在接口裏面,需要用到報警功能的類就需要實現這個接口中的open( )和close( ),也許這個類根本就不具備open( )和close( )這兩個功能,比如火災報警器。

從這裏可以看出, Door的open() 、close()和alarm()根本就屬於兩個不同範疇內的行爲,open()和close()屬於門本身固有的行爲特性,而alarm()屬於延伸的附加行爲。因此最好的解決辦法是單獨將報警設計爲一個接口,包含alarm()行爲,Door設計爲單獨的一個抽象類,包含open和close兩種行爲。再設計一個報警門繼承Door類和實現Alarm接口。

interface Alram {
    void alarm();
}
 
abstract class Door {
    void open();
    void close();
}
 
class AlarmDoor extends Door implements Alarm {
    void oepn() {
      //....
    }
    void close() {
      //....
    }
    void alarm() {
      //....
    }
}

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