接口和內部類爲咱們提供了一種將接口與實現分離的更加結構化的方法。設計模式
9.1抽象類和抽象方法工具
若是咱們的基類只是但願它被繼承從而經過它的接口操做導出類,它自己建立對象沒有什麼意義,那麼咱們能夠把這個基類設計爲抽象類。把在基類中很差實現的方法標記爲abstract。這樣作可使類的抽象性更加明確。spa
9.2接口設計
interface關鍵字使得抽象概念更加完全,只提供了形式,沒有任何實現。但它不單單是極度抽象的類,它還容許建立出一個能夠向上轉型成多種類型的類,來實現相似於多重繼承的特性。對象
接口中也能夠包含域,但這些域是隱式static final的。繼承
接口中的方法必須是public(可省略不寫),實現類中實現方法也必須是public的。接口
9.3徹底解耦get
只要一個方法操做的是類而非接口,那麼你就只能使用這個類及其子類。若是這個方法還想操做其餘類型,就會發生錯誤。而接口就可大大放寬這種限制,使得咱們能夠編寫複用性高的代碼。例如:有一個手機類,接口是播放器play(),有不一樣的導出類繼承這個手機類,一個方法接收手機對象,調用play方法播放音樂。可是這個方法只能接收手機對象和導出類對象。若是我想讓電腦播放音樂,因爲電腦不屬於手機繼承體系,因此不能實現這種功能。可是若是咱們把播放功能抽象到一個接口裏,讓手機實現這個接口,電腦實現這個接口,那麼這個方法只要接收接口參數便可。實現瞭解耦合。io
若是手機類是咱們建立的,咱們能夠直接添加implements,可是若是它是jar裏的或者別人的,咱們不能直接修改它怎麼辦呢?擴展
可使用適配器模式,建立一個適配器類,實現接口,組合所須要的對象,在方法裏調用該對象相應的方法。
9.4Java中的多重繼承
必定要記住:使用接口的核心緣由就是爲了能向上轉型成多個基類(以及由此帶來的靈活性),第二個緣由就是與使用抽象類相同:防止客戶端建立該類的對象。
9.5經過繼承擴展接口
利用extends關鍵字能夠擴展接口裏的方法
9.6適配接口
使用適配器模式來給現有操做接口方法添加新的操做對象是很是有用的。
9.7接口中的域
隱式的static、final的,在enum出現以前(Java SE5)用它當作常量。
9.8嵌套接口
...
9.9接口與工廠
接口是實現多繼承的途徑,而生成遵循接口對象的典型方式就是工廠方法設計模式。
原始方式:
方法以接口爲參數,void action(Service s){...}
調用的時候if(xxx)action(new SImp1());else if(xxx)action(new SImp2());else if....每一個調用地方都須要直接提供實現類對象。若是須要修改/增長實現類代碼就會很冗餘。
工廠方式:
void action(ServiceFactory fac){Service s = fac.getService();....}
只須要在factory裏改變便可。
9.10總結
任何抽象性都應該是應真正需求而產生的。應該優先選擇類而不是接口。若是接口的必需性變得很是明確,那麼就進行重構。接口是重要的工具,可是不要濫用它。