此次介紹結構型設計模式中的第二種模式,橋接模式。 使用橋接模式的目的就是爲了解耦,鬆散的耦合更利於擴展,可是會增長相應的代碼量和設計難度。html
橋接模式是爲了將抽象化與實現化解耦,讓兩者能夠獨立地變化。方便對每一部分的擴展,以及單獨的維護。抽象化的一方與實現化的一方之間創建一個橋樑,這樣二者的依賴關係就能夠經過這個橋樑來創建了。編程
三個小動物要過河,分別是小豬,小雞,小馬,小豬要去河對面的空地曬太陽,小雞要去河對面的小樹林裏找蟲子吃,小馬要去河對面的草地裏吃草。那麼它們三個都要通過小橋才能過河。有了場景下面來講一下代碼的實現,先建立一個小橋的接口。設計模式
/** * 小橋 */ public interface Bridge { /** * 目的地 */ void targetLand(); }
由於三個小動物的目的地不同,因此每個目的地對應一個實現。ide
小豬的目的地post
/** * 空地 */ public class VacantLand implements Bridge{ /** * 目的地 */ @Override public void targetLand() { System.out.println("空曠的地方,曬太陽"); } }
小雞的目的地學習
/** * 小樹林 */ public class Forest implements Bridge{ /** * 目的地 */ @Override public void targetLand() { System.out.println("小樹林,覓食。"); } }
小馬的目的地測試
/** * 草地 */ public class Grassland implements Bridge{ /** * 目的地 */ @Override public void targetLand() { System.out.println("大草原,盡情奔騰。"); } }
下面來實現抽象化的部分,每一個小動物都要過橋去往不一樣的目的地,因此它們都要相同的過橋行爲。因此定義一個動物抽象類。url
/** * 小動物 */ public abstract class Animal { /** * 橋 */ Bridge bridge; /** * 過橋 */ abstract void willToDo(); }
小豬spa
/** * 小豬 */ public class Piglet extends Animal { /** * 過橋 */ @Override public void willToDo() { System.out.println("我是小豬要過橋去 "); } }
小雞設計
/** * 小雞 */ public class Chick extends Animal { /** * 過河橋 */ @Override public void willToDo() { System.out.println("我是小雞要過橋去 "); } }
小馬
/** * 小馬 */ public class Pony extends Animal { /** * 過橋 */ @Override public void willToDo() { System.out.println("我是小馬要過橋去 "); } }
測試例子
public class TestBridge { public static void main(String[] args) { Animal animal = new Chick(); animal.bridge = new Forest(); animal.willToDo(); animal.bridge.targetLand(); } }
運行結果
我是小雞要過橋去
小樹林,覓食。
這就是一個完整的橋接模式的例子,這樣使得小動物和要去的目的地解耦了。若是再來了一個小動物,例如小鴨子,它只須要繼承Animal類便可,若是它的目的地已經存在了就直接使用現有的目的地類,若是要去的目的地不存在(例如小鴨子要去池塘),那麼能夠再建立一個池塘的目的地,而後實現自Bridge就能夠了。
下面來介紹一下橋接模式的結構,以下圖所示。
從上面的結構圖中咱們能夠看出來,橋接模式實際上是分爲四個角色的。
抽象化角色(Animal類):定義抽象化,並保存一個對實現化對象的引用。
抽象化擴展角色(Chick、Piglet、Pony等具體的小動物類):實現和擴展抽象化角色的功能。
實現化角色(Bridge接口):此角色給出了實現化角色的接口,定義了實現化角色的行爲。
具體實現化角色(VacantLand、GrassLand、Forest等目的地類):實現化角色接口的具體實現類。
一、分離抽象和實現部分:
分離了抽象和實現部分,提升了系統的靈活性,這樣有助於對系統進行分層,從而產生更好的結構化的系統。
二、更好的擴展性:
由於抽象部分和實現部分分離開了,因此這兩部分能夠獨立擴展,互不影響,大大提升了系統的可擴展性。
三、可動態切換:
因爲分離了抽象和實現,那麼在實現橋接的時候,能夠實現動態的選擇和使用具體的實現,也就是在運行期間動態切換實現。
四、減小了子類的數量:
從抽象和實現兩個維度來看,若是不是用橋接模式的話,這兩個維度的子類,在發生變化時影響到的數量是兩個維度子類的乘積。而使用了橋接模式後影響到的數量是兩個維度的子類的和。
增長了系統的理解和設計難度,入手並非那麼容易了,由於聚合關係定義在抽象層,因此須要開發者對抽象進行設計和編程。
想了解更多的設計模式請查看Java設計模式學習記錄-GoF設計模式概述。