標籤:c++ 物件導向 設計模式 命令模式
命令模式(Command):將一個請求封裝為一個對象,從而使我們可用不同的請求對客戶進行參數化,對請求排隊或記錄請求日誌,以及支援可撤銷的操作。
命令模式的優點:
第一、能較容易的設計一個命令隊列。
第二、在需要的情況下,可用較容易地將命令計入日誌。
第三、允許接受請求的一方決定是否需要否決請求。
第四、可用容易地實現對請求的撤銷和重做。
第五、由於加進新的具體命令類不影響其他的類,因此增加新的具體命令類很容易、
關鍵優點:把請求一個操作的對象與知道怎麼執行一個操作的對象分割開。
如果不清楚一個系統是否需要命令模式,一般就不要著急去實現它,事實上,在需要的時候通過重構實現這個模式並不困難,只有在真正需要如撤銷和恢複操作等功能時,把原來的代碼重構為命令模式才有意義。
#ifndef COMMAND_H#define COMMAND_H#include<iostream>#include<string>#include<list>using namespace std;class Barbecuer{public:void BakeMutton(){cout << "烤羊肉串。\n";}void BakeChickenWing(){cout << "烤雞翅。\n";}};class Command{protected:Barbecuer receiver;public:Command(){}Command(Barbecuer & b) :receiver(b){}virtual void ExcuteCommand() = 0;};class BakeMuttonCommand :public Command{public:BakeMuttonCommand(Barbecuer & b) { receiver = b; }void ExcuteCommand(){ receiver.BakeMutton(); }};class BakeChickenWingCommand :public Command{public:BakeChickenWingCommand(Barbecuer & b) { receiver = b; }void ExcuteCommand(){ receiver.BakeChickenWing(); }};class Waiter{list<Command *>orders;public:void SetOrder(Command * comptr);void CancelOrder(Command * comptr);void Notify();};void Waiter::SetOrder(Command * comptr){orders.push_back(comptr);cout << "增加訂單\n";}void Waiter::CancelOrder(Command * comptr){orders.remove(comptr);cout << "取消訂單\n";}void Waiter::Notify(){for each (Command * var in orders){var->ExcuteCommand();}}#endif
#include "Command.h"int main(){Barbecuer boy;BakeChickenWingCommand bakechickenwingcommand1(boy);BakeChickenWingCommand bakechickenwingcommand2(boy);BakeMuttonCommand bakemuttoncommand1(boy);BakeMuttonCommand bakemuttoncommand2(boy);Waiter girl;girl.SetOrder(&bakechickenwingcommand1);girl.SetOrder(&bakechickenwingcommand2);girl.SetOrder(&bakemuttoncommand1);girl.SetOrder(&bakemuttoncommand2);girl.Notify();girl.CancelOrder(&bakechickenwingcommand2);girl.Notify();return 0;}
設計模式C++實現十九:命令模式