IronMan之工廠
前言
實用爲主,學一些用得到的技術更能在如今的社會裏保命。 雖然在日常的工作中設計模式不是經常的用到,但是呢,學習它只有好處沒有壞處。
設計模式像是一種「標籤」,它是代碼編寫者思想的體現。有木有感覺到這樣很便捷?看到一些代碼的時候就很清楚的瞭解編寫者的思想了,這是爲什麼呢?因爲編寫者們用了「標籤」,而你恰恰是知道「標籤」意思的。 跟一異曲同工,在學習框架、瞭解框架的對象模型的時候,「標籤」是時常出現,如果你不瞭解「標籤」的意思那多痛苦啊!!!!! 還有好多,不去一一闡述了。
工作中需求的變更時常令我們頭疼不已,總是要按着需求來重新的修改代碼,然後發佈新的產品版本,或者是出更新包。 在需求變更中,對應着代碼也要修改,但是這修改也是分層次的。比如修改的模板在當初設計的時候遵循了開閉原則(OCP)的話,代碼的修改就變的輕鬆的多了。
我想製造出一個像電影《鋼鐵俠》裏面那樣的的一身盔甲,又或者說是機器吧,我把這個想法告訴了我的朋友們,他們都認爲我瘋了。
好吧,我說的是用代碼抽象的製造出」鋼鐵俠「
廢話不多說,下面這個系列是用鋼鐵俠(IronMan)作爲主題的設計模式 今天來學習簡單工廠模式、工廠方法模式、以及抽象工廠模式。
問題的發現
需求:
「玩具廠」有一天找到我說:「Jin叫獸我們這需要一些部件,我們會提供「圖紙」,請您幫忙製造,您看有問題嗎?」。
我:「當然沒有問題了。很樂意幫助你們」。
「玩具廠」:「噢!好的。Jin叫獸,時間方面還有什麼問題嘛?」
我:「沒問題的,我會盡快的」。
「玩具廠」:「那真的太感謝您了,Jin叫獸。我們就不打擾您了,先走了。」
我:「晚上一起吃頓飯吧」。
「玩具廠」:「Jin叫獸不必客氣啊」。
我:「好,你們慢走」。
生產車間:
「一點挑戰性都沒有,隨隨便便就製造出來了。先從組成‘鋼鐵俠’的部件開始生產吧。」
既然是這樣,那就從部件開始生產吧。
這裏是「玩具廠」提供的「鋼鐵俠」右臂的「圖紙」:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
|
1
public
class
RightHandComponent
2 {
3
public
RightHandComponent()
4 {
5
this
.strName =
"毅代先鋒號一代右部件"
;
6
7 }
8
public
RightHandComponent(
string
strname)
9 {
10
this
.strName = strname;
11 }
12
private
string
strName =
string
.Empty;
13
public
string
Name
14 {
15
get
{
return
strName; }
16
set
{ strName = value; }
17 }
18 }
|
還有一個左臂部件的「圖紙」:
1
2
3
4
5
6
7
8
9
10
11
12
13
|
1
public
class
LeftHandComponent
2 {
3
public
LeftHandComponent()
4 {
5
this
.strName =
"毅代先鋒號一代左部件"
;
6 }
7
private
string
strName =
string
.Empty;
8
public
string
Name
9 {
10
get
{
return
strName; }
11
set
{ strName = value; }
12 }
13 }
|
還有若干「圖紙」…… 不在這篇一一列舉了,在後面文章中會全面的講解到。
開始生產
1
2
|
RightHandComponent rightcomponent =
new
RightHandComponent();
LeftHandComponent leftcomponent =
new
LeftHandComponent();
|
若干的部件
被我一個個的按照圖紙給製造了出來。
這樣就可以拿rightcomponent、leftcomponent……等等的一些製造好的部件組裝了。
我也可以給「玩具廠」打電話了,可以交貨收錢。可是電話打完情況又變了,
中間的對話就不說了,「玩具廠」的意思就是這樣的。比如說「運輸途中」出現「損壞」,他們希望用一個很快捷便利的方式能得到部件。
簡單工廠
嗯,我想了一下,不過對於我Jin叫獸來說都是小事,待我造出來一臺部件生產器來。他們拿着機器自己回家生產不就ok了。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
|
public
class
IronManComponentFactory
{
public
static
object
CreateComponent(
string
comname)
{
switch
(comname)
{
case
"RightCom"
:
return
new
RightHandComponent();
case
"LeftCom"
:
return
new
LeftHandComponent();
等等……
}
return
null
;
}
}
|
這樣生產的「機器」就好了,我得自己試用一下,看看效果怎麼樣。
1
2
|
1 RightHandComponent rightcomponent = IronManComponentFactory.CreateComponent(
"RightCom"
)
as
RightHandComponent;
2 LeftHandComponent leftcomponent = IronManComponentFactory.CreateComponent(
"LeftCom"
)
as
LeftHandComponent;
|
這樣反而多此一舉了,第一步,向機器輸入了命令以便自己獲得想要的部件,第二步,在生產出來後我還得把「圖紙」拿過來比對一下。 在我一籌莫展的時候,「玩具廠」給我發了個郵件,給我發了一份「部件規範說明書」,要求我的機器生產出的部件是達到說明書標準的。
那我們就來看一下這個所謂的「部件規範說明書」
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
|
1
public
abstract
class
Component
2 {
3
private
string
strName =
string
.Empty;
4
/// <summary>
5
/// 名稱
6
/// </summary>
7
public
string
Name
8 {
9
get
{
return
strName; }
10
set
{ strName = value; }
11 }
12
/// <summary>
13
/// 自我描述
14
/// </summary>
15
public
abstract
void
Self_Described();
16 }
|
看完這個「部件規範說明書」,我已經無力吐槽,沒辦法了,只有重新設計部件了,「圖紙」要重新繪製,因爲要按照那該死的「規範說明書」。
再看一下各個部件的「圖紙」
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
|
1
public
class
RightHandComponent:Component
2 {
3
public
RightHandComponent()
4 {
5
base
.Name =
"毅代先鋒號一代右部件"
;
6
//fWeight=材質輸出
7 }
8
public
RightHandComponent(
string
strname)
9 {
10
base
.Name = strname;
11 }
12
public
override
void
Self_Described()
13 {
14 Console.WriteLine(
base
.Name);
15 }
16 }
17
public
class
LeftHandComponent:Component
18 {
19
public
LeftHandComponent()
20 {
21
base
.Name =
"毅代先鋒號一代左部件"
;
22 }
23
public
LeftHandComponent(
string
strname)
24 {
25
base
.Name = strname;
26 }
27
public
override
void
Self_Described()
28 {
29 Console.WriteLine(
base
.Name);
30 }
31 }
|
等等一些部件……
這下我再把原來的搭好的「生產機器」拆了,內部修改一下,來看一下修改後的「機器」
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
|
1
public
class
IronManComponentFactory
2 {
3
public
static
Component CreateComponent(
string
comname)
4 {
5
switch
(comname)
6 {
7
case
"RightCom"
:
8
return
new
RightHandComponent();
9
case
"LeftCom"
:
10
return
new
LeftHandComponent();
11
12 }
13
return
null
;
14 }
15 }
|
自己來測試一下:
1
2
3
4
|
1 Component rightcomponent = IronManComponentFactory.CreateComponent(
"RightCom"
);
2 Component leftcomponent = IronManComponentFactory.CreateComponent(
"LeftCom"
);
3 rightcomponent.Self_Described();
4 leftcomponent.Self_Described();
|
於是,我很放心的就交給了「玩具廠」使用了,還得了個好評。
工廠方法
好景不長,「玩具廠」再次來電,提出一個要求,想讓我的「生產機器」裏面還可以生產更多的符合「部件規範說明書」的部件。
這樣說來是要改裝「生產機器」了。 可以說「玩具廠」是故意的,絕對是故意的。這下整蒙圈了,虧血本了,「生產機器」又要拆了…… 直接來看「生產機器」的圖紙
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
|
1
public
abstract
class
IronManComponentFactory
2 {
3
protected
string
factoryName =
string
.Empty;
4
protected
void
InitDataMessage()
5 {
6 Console.WriteLine(
"生產機器:"
+ factoryName +
".準備就緒"
|