工作中,我們經常需要建立一組物件,這組物件相互相關或者依賴,形成乙個系列,系列中的物件不能與其他系列中的物件混用。為系列中的每種物件建立工廠可以滿足物件建立的需求,但是無法保證它們是同一系列的。這時引入抽象工廠模式可以解決上面的問題。下面是gof給出的抽象工廠模式的意圖。
提供乙個建立一系列相關或相互依賴物件的介面,而無需指定它們具體的類。抽象工廠的優點:
1、客戶端不依賴具體實現類,符合依賴倒置的oo原則;
2、可以生成一系列的物件,生成不同的系列的切換比較方便,同時也可以保證一致性;
但是如果在新的系列中增加新型別,將會引發所有工廠類的修改。
如果注意觀察,會發現很多框架的擴充套件點就是使用抽象工廠模式實現的,比如wcf、unity等等。
抽象工廠模式比較常用,而且主要的是為了實現依賴倒置,所以實際中很多情況下都是用di框架完成實現了。
抽象工廠的類圖相對比較複雜,不過本質就是表達了,客戶端依賴幾個抽象,而不是這些抽象的具體實現的依賴倒置關係。為了便於描述,下面將系列中包含的型別稱為產品,即下圖中有兩種產品a和b,以及兩個系列1和2。
模式的參與者如下:
1、抽象工廠,提供了建立系列中各個產品的抽象方法——abstractfactory;
2、具體的工廠實現,用來建立某乙個系列的產品——factory1、factory2;
3、產品的抽象——iproducta、iproductb;
4、每個系列的產品具體實現——producta1、producta2、productb1、productb2;
5、客戶端類,只依賴於1和3的抽象——client。
假設我們有乙個網頁,需要提供兩種風格的頭和尾(比如男性版和女性版)。這兩種風格的頭尾當然不能混用,否則效果將是慘不忍睹。所以要嘛使用風格1,要嘛使用風格2,兩種風格構成了兩個系列,頁面頭部和尾部構成了系列中的兩個產品。下面用抽象工廠實現。
1、定義頁面頭部的介面iheader。
1:using system;
2:
3:namespace designpatterns.abstractfactory
4:
12: }
13:2、提供iheader介面的兩個實現。
styleaheader:
1:using system;
2:
3:namespace designpatterns.abstractfactory
4:
14: }
15: }
16:stylebheader:
1:using system;
2:
3:namespace designpatterns.abstractfactory
4:
14: }
15: }
16:3、定義頁面尾部的介面ifooter。
1:using system;
2:
3:namespace designpatterns.abstractfactory
4:
12: }
13:4、提供ifooter介面的兩個實現。
styleafooter:
1:using system;
2:
3:namespace designpatterns.abstractfactory
4:
14: }
15: }
16:stylebfooter:
1:using system;
2:
3:namespace designpatterns.abstractfactory
4:
14: }
15: }
16:5、實現抽象工廠abstractstylefactory,這裡只做演示,實際應用中應該用技術手段去除生成工廠時的分支判斷。
1:using system;
2:
3:namespace designpatterns.abstractfactory
4:
27:return instance;
28: }
29: }
30:
31:public abstract
iheader createheader();
32:public abstract
ifooter createfooter();
33: }
34: }
35:6、具體工廠實現。
styleafactory:
1:using system;
2:
3:namespace designpatterns.abstractfactory
4:
14:
15:public override
ifooter createfooter()
16:
19: }
20: }
21:stylebfactory:
1:using system;
2:
3:namespace designpatterns.abstractfactory
4:
14:
15:public override
ifooter createfooter()
16:
19: }
20: }
21:7、客戶端**。
1:using system;
2:
3:namespace designpatterns.abstractfactory
4:
24: }
25: }
26:8、執行檢視結果。
上面的例子比較簡單,博文提供了更加貼近實際的乙個示例,可以參考。
溫故知新 ROWTYPE
rowtype 相當於資料庫表裡的一行資料記錄的變數型別。declare 定義乙個emp表裡的一行記錄的資料型別的變數 v emp emp rowtype begin 查詢的emp表裡的資料列必須與v emp的列順序以及個數保持一致 select empno,ename,job,mgr,hireda...
vue 溫故知新
v cloak指令 解決變數閃爍問題 v if isshow 是插入或刪除節點 v show isshow 是隱藏或顯示節點 v bind data m msg 或 data m msg 繫結屬性 v bind key v.id 繫結乙個資料唯一值,用於虛擬dom演算法,優化渲染效率 v on cl...
溫故知新系列
我從事windows phone開發一年多來,終日忙於開發應用,每每有所收穫也沒有時間思考總結。最近實習即將結束,同時也看清了真實的生活,痛定思痛,決定好好整理自己所學所得,同時也靜下心來好好學習一下一直欠缺的知識。溫故而知新,可以為師矣。此番總結,不求為師,但求能看清自己,共勉共勉。此溫故知新系列...