生活随笔
收集整理的這篇文章主要介紹了
C++之命令(Command)模式
小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.
0. 簡(jiǎn)介
我們?cè)谟龅筋愃艷UI中多種Button點(diǎn)擊功能的操作時(shí),我們應(yīng)該將請(qǐng)求的所有細(xì)節(jié) (例如調(diào)用的對(duì)象、 方法名稱和參數(shù)列表) 抽取出來(lái)組成命令類, 該類中僅包含一個(gè)用于觸發(fā)請(qǐng)求的方法。
命令模式就是這樣一種行為設(shè)計(jì)模式, 它可將請(qǐng)求轉(zhuǎn)換為一個(gè)包含與請(qǐng)求相關(guān)的所有信息的獨(dú)立對(duì)象。 并能根據(jù)不同的請(qǐng)求將方法參數(shù)化、 延遲請(qǐng)求執(zhí)行或?qū)⑵浞湃腙?duì)列中, 且能實(shí)現(xiàn)可撤銷操作。
1. 命令模式示意圖
命令模式可將特定的方法調(diào)用轉(zhuǎn)化為獨(dú)立對(duì)象。 這一改變也帶來(lái)了許多有趣的應(yīng)用: 你可以將命令作為方法的參數(shù)進(jìn)行傳遞、 將命令保存在其他對(duì)象中, 或者在運(yùn)行時(shí)切換已連接的命令等。
Command(抽象命令類):抽象出命令對(duì)象,可以根據(jù)不同的命令類型。寫出不同的實(shí)現(xiàn)類
Concrete Command(具體命令類):實(shí)現(xiàn)了抽象命令對(duì)象的具體實(shí)現(xiàn)
Invoker(調(diào)用者/請(qǐng)求者):請(qǐng)求的發(fā)送者,它通過(guò)命令對(duì)象來(lái)執(zhí)行請(qǐng)求。一個(gè)調(diào)用者并不需要在設(shè)計(jì)時(shí)確定其接收者,因此它只與抽象命令來(lái)之間存在關(guān)聯(lián)。在程序運(yùn)行時(shí),將調(diào)用命令對(duì)象的execute() ,間接調(diào)用接收者的相關(guān)操作。
Receiver(接收者):接收者執(zhí)行與請(qǐng)求相關(guān)的操作,真正執(zhí)行命令的對(duì)象。具體實(shí)現(xiàn)對(duì)請(qǐng)求的業(yè)務(wù)處理。未抽象前,實(shí)際執(zhí)行操作內(nèi)容的對(duì)象。
Client(客戶端):在客戶類中需要?jiǎng)?chuàng)建調(diào)用者對(duì)象,具體命令類對(duì)象,在創(chuàng)建具體命令對(duì)象時(shí)指定對(duì)應(yīng)的接收者。發(fā)送者和接收者之間沒(méi)有之間關(guān)系。都通過(guò)命令對(duì)象來(lái)調(diào)用。
2. 示例程序
責(zé)任鏈模式和命令模式用于處理請(qǐng)求發(fā)送者和接收者之間的不同連接方式。責(zé)任鏈按照順序?qū)⒄?qǐng)求動(dòng)態(tài)傳遞給一系列的潛在接收者, 直至其中一名接收者對(duì)請(qǐng)求進(jìn)行處理。命令模式則是在發(fā)送者和請(qǐng)求者之間建立單向連接。
作為命令模式的作用,非常明顯,它可以通過(guò)某些行為來(lái)參數(shù)化對(duì)象。從而避免了繼承導(dǎo)致的調(diào)用與接收的緊耦合。命令模式則是分離了這兩者,修改時(shí)只需要添加接收者并創(chuàng)建新的實(shí)例化具體命令類即可實(shí)現(xiàn)整套代碼的調(diào)用。
#include <iostream>
#include <string>
#include <vector>
#include <algorithm>
#include <iterator>using namespace std
;
class Receiver
{
public:void BakeMutton(){cout
<< "烤羊肉"<< endl
;}void BakeChicken(){cout
<< "烤雞翅"<< endl
;}
};
class Command
{
public:Command(Receiver
* pstReceiver
):m_pstReceiver(pstReceiver
){}virtual void Excute() = 0;protected:Receiver
* m_pstReceiver
;
};
class ConcreteCommandA: public Command
{
public:ConcreteCommandA(Receiver
* pstReceiver
):Command(pstReceiver
){}virtual void Excute(){cout
<< "ConcreteCommandA excuting......"<< endl
;m_pstReceiver
->BakeMutton();}};
class ConcreteCommandB: public Command
{
public:ConcreteCommandB(Receiver
* pstReceiver
):Command(pstReceiver
){}virtual void Excute(){cout
<< "ConcreteCommandB excuting......"<< endl
;m_pstReceiver
->BakeChicken();}
};
class Invoke
{
public:void Add(Command
* pstCommand
){m_vecPstCommand
.push_back(pstCommand
);}void Remove(Command
* pstCommand
){m_vecPstCommand
.erase(find(m_vecPstCommand
.begin(), m_vecPstCommand
.end(), pstCommand
));}void RemoveAll(){m_vecPstCommand
.clear();}void Notify(){for (typeof(m_vecPstCommand
.begin()) it
= m_vecPstCommand
.begin(); it
!= m_vecPstCommand
.end(); ++it
){(*it
)->Excute();}}private:vector
<Command
*> m_vecPstCommand
;
};int main(int argc
, char* argv
[])
{Receiver
* pstReceiver
= new Receiver();Command
* pstConcreteCommandA
= new ConcreteCommandA(pstReceiver
);Command
* pstConcreteCommandB
= new ConcreteCommandB(pstReceiver
);Invoke
* pstInvoke
= new Invoke();pstInvoke
->Add(pstConcreteCommandA
);pstInvoke
->Add(pstConcreteCommandA
);pstInvoke
->Add(pstConcreteCommandB
);pstInvoke
->Notify();cout
<< "------------------"<< endl
<< endl
;pstInvoke
->Remove(pstConcreteCommandA
); pstInvoke
->Remove(pstConcreteCommandB
);pstInvoke
->Notify();cout
<< "------------------"<< endl
<< endl
;return 0;
}
…詳情請(qǐng)參照古月居
總結(jié)
以上是生活随笔為你收集整理的C++之命令(Command)模式的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
如果覺(jué)得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。