意圖
將抽象部分與實現部分分離,使它們都可以獨立的變化。
場景
還是說我們要做的網絡游戲,多個場景需要擴充的問題我們已經采用了創建型模式來解決。現在的問題就是,不僅僅是游戲場景會不斷擴充,而且游戲的模式也在不斷擴充。比如,除了最基本的戰斗模式之外,還會有道具模式,金幣模式等。
對於這種在多個維度上都會有變化或擴充需求的項目來說,可以考慮引入橋接模式。或許你會說,不管是什麼場景,不管什麼模式,都可以是抽象場景的一個子類,但是,如果這樣的話,4個場景和3種模式就會產生12個子類,而10個場景5種模式就會有50個子類。一味進行繼承並不是什麼好方法,橋接模式的思想是把繼承轉化為組合,把乘法(10*5=50)轉化為加法(10+5=15)。
示例代碼
using System;
using System.Collections.Generic;
using System.Text;
namespace BridgeExample
{
class Program
{
static void Main(string[] args)
{
PatrixScene halfPaper = new HalfPaper();
halfPaper.Mode = new GoldMode();
halfPaper.LoadScene();
PatrixScene matrix = new Matrix();
matrix.Mode = new PrpoertyMode();
matrix.LoadScene();
}
}
abstract class PatrixScene
{
protected GameMode mode;
public GameMode Mode
{
get { return mode; }
set { mode = value; }
}
public abstract void LoadScene();
}
class HalfPaper : PatrixScene
{
public override void LoadScene()
{
Console.WriteLine("Load HalfPaper Completed");
mode.InitScene();
}
}
class Matrix : PatrixScene
{
public override void LoadScene()
{
Console.WriteLine("Load Matrix Completed");
mode.InitScene();
}
}
abstract class GameMode
{
public abstract void InitScene();
}
class PrpoertyMode : GameMode
{
public override void InitScene()
{
Console.WriteLine("Init Property Mode Completed");
}
}
class GoldMode : GameMode
{
public override void InitScene()
{
Console.WriteLine("Init Gold Mode Completed");
}
}
}
代碼執行結果如下圖:
代碼說明
l PatrixScene類是抽象化角色。雖然說針對第一維度也就是游戲場景,PatrixScene也是一個抽象,但是我覺得這裡說的抽象化和實現化還是針對第二維度的,也就是游戲模式。
l GameMode類就是實現化角色。你或許會說對於多個維度,把哪個作為抽象化角色呢?雖然維度是一個平行的概念,但是對於Bridge模式來說,我覺得它是把相對高層的角色作為抽象化角色,而把比較底層的操作作為實現化角色的。比如,對於場景和模式來說,模式是為場景服務的,我們就把場景作為抽象化角色。
l HalfPaper和Matrix都是修正抽象化角色。按照GOF的定義是說修正父類的抽象化定義。其實,我覺得抽象化角色不一定必須是對方法有默認實現,並且由子類進行修正。
l PropertyMode和GoldMode是具體實現化角色。它們用來實現實現化角色定義的接口。
l 從一個角度來說,抽象化和修正抽象化角色相對應實現化和具體實現化角色,從另外一個角度來說,抽象化和實現化角色對應修正抽象化和具體實現化角色。
l 客戶端代碼中直接選擇合適的具體實現化角色。看到這裡,你可能覺得和策略模式很像。其實,策略模式針對面更小一點,一是針對算法替換,二是只針對一個維度的變化點,因此它也就只有一個抽象角色。
何時采用
l 從代碼角度來說,如果類型的繼承是處於2個目的(違背單一職責原則)的話可以使用Bridge模式避免過多的子類。
l 從應用角度來說, 如果應用會在多個維度上進行變化,客戶端希望兩個維度(場景、游戲模式)的對象相對獨立,動態耦合(客戶端決定哪個場景和哪個游戲模式耦合)的時候可以考慮Bridge模式。
實現要點
l 選擇合適的類型作為抽象化角色(第一維度)。
l 抽象化角色和實現化角色通過組合進行關聯。
l 抽象和實現不綁定,允許客戶端作切換。
注意事項
l 無