作者poyenc (高髮箍)
看板C_and_CPP
標題Re: [問題] factory pattern
時間Sat Nov 19 05:12:10 2011
我想應該至少都要有像 《GoF》整理出來的細項,也要有《深入淺
出物件導向分析與設計》中頻繁出現的 user scenario,這本書才
算合格。
從沒有使用任何重構技巧的程式碼開始講起:
class Coffee {};
class Milk {};
int main() {
Coffee coffee;
Milk milk;
}
夏天來了,商店老闆決定開始試賣果汁:
修改行數:2
class Juice {};
int main() {
// ...
Juice juice;
}
一位客人來了,他只喝咖啡:
修改行數:5+
class Customer {
void drink(Coffee &coffee);
};
int main() {
// ...
Customer customer;
customer.drink(coffee);
}
更多客人來了,什麼
飲料都有人喝:
修改行數:11+
class Customer {
void drink(Coffee &coffee);
void drink(Milk &milk);
void drink(Juice &juice);
};
int main() {
// ...
Customer customer;
customer.drink(coffee);
Customer customer1;
customer1.drink(milk);
Customer customer2;
customer2.drink(juice);
}
再這樣寫下去你會發現連多賣一種飲料都會出人命,因為多個
drink() 內實作差不多都相同,所以應該把它們合體:
class Customer {
void drink(
?);
};
怎樣才能同時接受多種型別輸入呢?不是強行硬轉,就是用
void*,優雅點改用父類別的參考來接,此時才需要引進新的
介面:
class Beverage {};
class Coffee :
public Beverage {};
class Milk :
public Beverage {};
class Juice :
public Beverage {};
class Customer {
void drink( Beverage &beverage );
};
又因為每種飲料會有各自的製程,像是咖啡就要打奶泡加肉桂等等
,兩杯咖啡的程式碼就像這樣:
Coffee coffee;
coffee.打奶泡();
coffee.加肉桂();
Coffee coffee2;
coffee2.打奶泡();
coffee2.加肉桂();
重複的程式碼應該寫成函式以便於重複利用,又因為物件所有權轉
移的語意(老闆給客人),用回傳參考或複製品來實作都是不洽當的
,因此你會有三種函式:
Coffee* getCoffee();
Milk* getMilk();
Juice* getJuice();
第一位客人本來是點咖啡,他想換果汁喝(著色是修改部分):
Customer customer;
Coffee *
coffee = get
Coffee();
customer.drink(*
coffee);
↓
Customer customer;
Juice *
juice = get
Juice();
customer.drink(*
juice);
為了讓修改最小化,用父類別的指標去接:
Customer customer;
Beverage *beverage = get
Coffee();
customer.drink( *beverage );
↓
Customer customer;
Beverage *beverage = get
Juice();
customer.drink( *beverage );
在這邊呼叫 get()系列的函式是寫死在程式碼裡的,為了提供執行
時期的彈性,可以再外包給一個負責整合的函式:
Beverage* getBeverage(
enum Menu menu ) {
switch( menu ) {
case COFFEE:
return getCoffee();
case MILK:
return getMilk();
case JUICE:
return getJuice();
}
return NULL;
}
再來就只是細部做改寫而已,架構都差不多...
在套用工廠模式時,進行每一步的理由都是明確的嗎?中間是不是
有跳過某些步驟?你所作的改變都是因為不得已而為嗎?
為了使用而使用不會為你帶來方便,反而會讓你忘記它們之所以存
在的原因,如果你看的書沒有教你這些,請把它丟了吧。
順帶一提,此文章串其實已經偏離語言討論有點遠了...
--
※ 發信站: 批踢踢實業坊(ptt.cc)
◆ From: 140.121.197.115
※ 編輯: poyenc 來自: 140.121.197.115 (11/19 05:20)
推 x000032001: 11/19 09:48
推 cgcheng:factory的話,這篇寫得不錯 11/19 16:58
推 VictorTom:推~~ 11/19 20:05
推 xatier:推! 11/22 00:25