22桥接模式(Bridge Pattern)
動機(Motivate):
????在軟件系統中,某些類型由于自身的邏輯,它具有兩個或多個維度的變化,那么如何應對這種“多維度的變化”?如何利用面向對象的技術來使得該類型能夠輕松的沿著多個方向進行變化,而又不引入額外的復雜度?
意圖(Intent):
????將抽象部分與實現部分分離,使它們都可以獨立的變化。
??? ?? ?? ?? ?? ?? ?? ?? ?? ?? ?? ------《設計模式》GOF
結構圖(Struct):
??? ?? ????????????
生活中的例子:? ????
??? 我想大家小時候都有用蠟筆畫畫的經歷吧。紅紅綠綠的蠟筆一大盒,根據想象描繪出格式圖樣。而毛筆下的國畫更是工筆寫意,各展風采。而今天我們的故事從蠟筆與毛筆說起。
??? 設 想要繪制一幅圖畫,藍天、白云、綠樹、小鳥,如果畫面尺寸很大,那么用蠟筆繪制就會遇到點麻煩。畢竟細細的蠟筆要涂出一片藍天,是有些麻煩。如果有可能, 最好有套大號蠟筆,粗粗的蠟筆很快能涂抹完成。至于色彩嗎,最好每種顏色來支粗的,除了藍天還有綠地呢。這樣,如果一套12種顏色的蠟筆,我們需要兩套 24支,同種顏色的一粗一細。呵呵,畫還沒畫,開始做夢了:要是再有一套中號蠟筆就更好了,這樣,不多不少總共36支蠟筆。
?
??? ? ? ???
?? 再看看毛筆這一邊,居然如此簡陋:一套水彩12色,外加大中小三支毛筆。你可別小瞧這"簡陋"的組合,畫藍天用大毛筆,畫小鳥用小毛筆,各具特色。
?
??? ?? ???
?? ??? 呵呵,您是不是已經看出來了,不錯,我今天要說的就是Bridge模式。為了一幅畫,我們需要準備36支型號不同的蠟筆,而改用毛筆三支就夠了,當 然還要搭配上12種顏料。通過Bridge模式,我們把乘法運算3×12=36改為了加法運算3+12=15,這一改進可不小。那么我們這里蠟筆和毛筆到 底有什么區別呢?
??? 實際上,蠟筆和毛筆的關鍵一個區別就在于筆和顏色是否能夠分離。【GOF95】橋梁模式的用意是"將抽象化 (Abstraction)與實現化(Implementation)脫耦,使得二者可以獨立地變化"。關鍵就在于能否脫耦。蠟筆的顏色和蠟筆本身是分不 開的,所以就造成必須使用36支色彩、大小各異的蠟筆來繪制圖畫。而毛筆與顏料能夠很好的脫耦,各自獨立變化,便簡化了操作。在這里,抽象層面的概念是: "毛筆用顏料作畫",而在實現時,毛筆有大中小三號,顏料有紅綠藍等12種,于是便可出現3×12種組合。每個參與者(毛筆與顏料)都可以在自己的自由度 上隨意轉換。
??? 蠟筆由于無法將筆與顏色分離,造成筆與顏色兩個自由度無法單獨變化,使得只有創建36種對象才能完成任務。Bridge模式將繼承關系轉換為組合關系,從而降低了系統間的耦合,減少了代碼編寫量。??
代碼實現:?
????
2?????{
3?????????protected?Color?c;
4?????????public?abstract?void?Paint();
5?
6?????????public?void?SetColor(Color?c)
7?????????{?this.c?=?c;?}
8?????}
?
2?????{
3?????????public?override?void?Paint()
4?????????{?Console.WriteLine("Using?big?brush?and?color?{0}?painting",?c.color);?}
5?????}
?
1???class?SmallBrush?:?Brush2?????{
3?????????public?override?void?Paint()
4?????????{?Console.WriteLine("Using?small?brush?and?color?{0}?painting",?c.color);?}
5?????}
?
1???class?Color2?????{
3?????????public?string?color;
4?????}
?
1?class?Red?:?Color2?????{
3?????????public?Red()
4?????????{?this.color?=?"red";?}
5?????}
?
1????class?Green?:?Color2?????{
3?????????public?Green()
4?????????{?this.color?=?"green";?}
5?????}
?
1???class?Blue?:?Color2?????{
3?????????public?Blue()
4?????????{?this.color?=?"blue";?}
5?????}
?
?1?????class?Program?2?????{
?3????public?static?void?Main()
?4???{
?5?????Brush?b?=?new?BigBrush();
?6?????b.SetColor(new?Red());
?7?????b.Paint();
?8?????b.SetColor(new?Blue());
?9?????b.Paint();
10?????b.SetColor(new?Green());
11?????b.Paint();
12?
13?????b?=?new?SmallBrush();
14?????b.SetColor(new?Red());
15?????b.Paint();
16?????b.SetColor(new?Blue());
17?????b.Paint();
18?????b.SetColor(new?Green());
19?????b.Paint();
20???}
適用性:???
???1.如果一個系統需要在構件的抽象化角色和具體化角色之間增加更多的靈活性,避免在兩個層次之間建立靜態的聯系。
??? ? 2.設計要求實現化角色的任何改變不應當影響客戶端,或者說實現化角色的改變對客戶端是完全透明的。
??? ? 3?.一個構件有多于一個的抽象化角色和實現化角色,系統需要它們之間進行動態耦合。
?? ?? 4?.雖然在系統中使用繼承是沒有問題的,但是由于抽象化角色和具體化角色需要獨立變化,設計要求需要獨立管理這兩者。
Bridge要點:???
?????1.Bridge模式使用“對象間的組合關系”解耦了抽象和實現之間固有的綁定關系,使得抽象和實現可以沿著各自的維度來變化。
??? ??? 2.所謂抽象和實現沿著各自維度的變化,即“子類化”它們,得到各個子類之后,便可以任意它們,從而獲得不同平臺上的不同型號。
??? ??? 3.Bridge模式有時候類似于多繼承方案,但是多繼承方案往往違背了類的單一職責原則(即一個類只有一個變化的原因),復用性比較差。Bridge模式是比多繼承方案更好的解決方法。
??? ??? 4.Bridge模式的應用一般在“兩個非常強的變化維度”,有時候即使有兩個變化的維度,但是某個方向的變化維度并不劇烈——換言之兩個變化不會導致縱橫交錯的結果,并不一定要使用Bridge模式。
創作挑戰賽新人創作獎勵來咯,堅持創作打卡瓜分現金大獎總結
以上是生活随笔為你收集整理的22桥接模式(Bridge Pattern)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 浦发梦卡之斗鱼联名卡年费是多少
- 下一篇: GetType和typeof的区别