一,概述
定义:命令模式将一个请求或者操作封装到一个命令对象中。允许系统使用不同的请求将客户端参数化,对请求排队或者记录请求日志,提供命令的撤销,恢复能力
优点:
1 命令模式使新的命令很容易被加入
2 允许接受请求方否决请求
3 可较容易地设计一个命令队列
4 可以实现对请求的Undo,Redo
5 可以将命令计入日志
二,示例
两个人 去吃烧烤,先路过一个烧烤摊,人多管理比较混乱,命令请求者跟命令实施者“紧耦合”。
人太对,没吃,然后去烧烤店,遇到了经典的命令模式:服务生负责记录命令,传递命令。厨师负责执行命令。顾客则发出命令
1)烧烤摊代码
#include <iostream>
using namespace std;
//烤肉串者
class Barbecuer
{
//烤羊肉
public:
void BakeMutton()
{
cout<<"烤羊肉串!"<<endl;
}
//烤鸡翅
void BakeChickenWing()
{
cout<<"烤鸡翅!"<<endl;
}
};
int main()
{
Barbecuer *boy = new Barbecuer();
boy->BakeMutton();
boy->BakeMutton();
boy->BakeMutton();
boy->BakeChickenWing();
boy->BakeMutton();
boy->BakeMutton();
boy->BakeChickenWing();
}
2)烧烤店(第一版)
缺点:客户点一个菜,服务员通知一下(不符合实际)。应该点菜完成后一次性通知
如果某一个菜没有了,不应该客户判断,应该服务员判断
客户点菜需要记录日志,以备结账使用。
#include <iostream>
using namespace std;
//烤肉串者
class Barbecuer//命令执行者
{
public:
void BakeMutton()
{
cout<<"烤羊肉串!"<<endl;
}
void BakeChickenWing()
{
cout<<"烤鸡翅!"<<endl;
}
};
//抽象命令
class Command//声明执行的接口
{
protected:
Barbecuer *receiver;
public:
Command(Barbecuer *receiver)
{
this->receiver = receiver;
}
//执行命令
virtual void ExcuteCommand()=0;
};
//服务员
class Waiter //Invoker类
{
private:
Command *command;
//设置订单
public:
void SetOrder(Command *command)
{
this->command = command;
}
//通知执行
void Notify()
{
command->ExcuteCommand();
}
};
//烤羊肉串命令
class BakeMuttonCommand :public Command
{
public:
BakeMuttonCommand(Barbecuer *receiver)
: Command(receiver)
{ }
void ExcuteCommand()
{
receiver->BakeMutton();
}
};
//烤鸡翅命令
class BakeChickenWingCommand :public Command
{
public:
BakeChickenWingCommand(Barbecuer *receiver)
: Command(receiver)
{ }
void ExcuteCommand()
{
receiver->BakeChickenWing();
}
};
int main()
{
//开店前的准备
Barbecuer *boy = new Barbecuer();
Command *bakeMuttonCommand1 = new BakeMuttonCommand(boy);// 烤羊肉
Command *bakeMuttonCommand2 = new BakeMuttonCommand(boy);
Command *bakeChickenWingCommand1 = new BakeChickenWingCommand(boy);//烤鸡翅
Waiter *girl = new Waiter();
//开门营业
girl->SetOrder(bakeMuttonCommand1);
girl->Notify();
girl->SetOrder(bakeMuttonCommand2);
girl->Notify();
girl->SetOrder(bakeChickenWingCommand1);
girl->Notify();
}
3)烧烤店(松耦合升级版)(C#)
static void Main(string[] args)
{
//开店前的准备
Barbecuer boy = new Barbecuer();
Command bakeMuttonCommand1 = new BakeMuttonCommand(boy);
Command bakeMuttonCommand2 = new BakeMuttonCommand(boy);
Command bakeChickenWingCommand1 = new BakeChickenWingCommand(boy);
Waiter girl = new Waiter();
//开门营业 顾客点菜
girl.SetOrder(bakeMuttonCommand1);
girl.SetOrder(bakeMuttonCommand2);
girl.SetOrder(bakeChickenWingCommand1);
//点菜完闭,通知厨房
girl.Notify();
Console.Read();
}
}
//服务员
public class Waiter
{
private IList<Command> orders = new List<Command>();
//设置订单
public void SetOrder(Command command)
{
if (command.ToString() == "命令模式.BakeChickenWingCommand")
{
Console.WriteLine("服务员:鸡翅没有了,请点别的烧烤。");
}
else
{
orders.Add(command);
Console.WriteLine("增加订单:" + command.ToString() + " 时间:" + DateTime.Now.ToString());
}
}
//取消订单
public void CancelOrder(Command command)
{
orders.Remove(command);
Console.WriteLine("取消订单:" + command.ToString() + " 时间:" + DateTime.Now.ToString());
}
//通知全部执行
public void Notify()
{
foreach (Command cmd in orders)
{
cmd.ExcuteCommand();
}
}
}
//抽象命令
public abstract class Command
{
protected Barbecuer receiver;
public Command(Barbecuer receiver)
{
this.receiver = receiver;
}
//执行命令
abstract public void ExcuteCommand();
}
//烤羊肉串命令
class BakeMuttonCommand : Command
{
public BakeMuttonCommand(Barbecuer receiver)
: base(receiver)
{ }
public override void ExcuteCommand()
{
receiver.BakeMutton();
}
}
//烤鸡翅命令
class BakeChickenWingCommand : Command
{
public BakeChickenWingCommand(Barbecuer receiver)
: base(receiver)
{ }
public override void ExcuteCommand()
{
receiver.BakeChickenWing();
}
}
//烤肉串者
public class Barbecuer
{
public void BakeMutton()
{
Console.WriteLine("烤羊肉串!");
}
public void BakeChickenWing()
{
Console.WriteLine("烤鸡翅!");
}
}
三,命令模式基本代码构成
#include <iostream>
using namespace std;
class Receiver//执行命令类
{
public:
void Action()
{
cout<<"执行请求!"<<endl;
}
};
class Command //声明执行操作的接口
{
protected:
Receiver *receiver;
public:
Command(Receiver *receiver)
{
this->receiver = receiver;
}
virtual void Execute()=0;
};
class Invoker//要求该命令执行这个请求
{
private:
Command *command;
public:
void SetCommand(Command *command)
{
this->command = command;
}
void ExecuteCommand()
{
command->Execute();
}
};
class ConcreteCommand :public Command //将一个接收者对象绑定于一个动作
{
public:
ConcreteCommand(Receiver *receiver):Command(receiver)
{ }
void Execute() //实现命令接口
{
receiver->Action();
}
};
int main()
{
Receiver *r = new Receiver();//命令的真正执行类 (后台厨师)
Command *c = new ConcreteCommand(r);//将命令绑定到 命令执行者 (顾客)
Invoker *i = new Invoker();//要求命令执行者执行命令(记账单的小生)
// Set and execute command
i->SetCommand(c);
i->ExecuteCommand();
system("pause");
}
分享到:
相关推荐
virtual keyboard software of GEE-UR-2000 UHF RFID READER
新疆烤羊肉串正宗技法:内地羊肉串腌制及香料水配比.pdf
设计模式作业——用命令模式编写的烧烤店。
Head.First.设计模式.中文版 1 欢迎来到设计模式世界:设计模式入门 模拟鸭子应用 Joe想到继承 利用接口如何?...6 命令模式:封装调用 7 适配器模式与外观模式:随遇而安 8 模板方法模式:封装算法
airmate艾美特迷你无烟烤盘 2020年-改- 20200805 说明书.pdf
6 命令模式 封装调用 7 适配器模式与外观模式 随遇模式 8 模板方法模式 封装算法 9 选代器与组合模式 管理良好的集合 10 状态模式 事物的状态 11 代理模式 控制对象访问 12 复合模式 模式中的模型 13 与设计模式相处...
6 命令模式 封装调用 7 适配器模式与外观模式 随遇模式 8 模板方法模式 封装算法 9 选代器与组合模式 管理良好的集合 10 状态模式 事物的状态 11 代理模式 控制对象访问 12 复合模式 模式中的模型 13 与设计模式相处...
烤漆设备行业(2021-2026)企业市场突围战略分析与建议.docx
烘烤设备行业(2021-2026)企业市场突围战略分析与建议.docx
烘烤机械行业(2021-2026)企业市场突围战略分析与建议.docx
复烤烟叶行业(2021-2026)企业市场突围战略分析与建议.docx
第12章介绍如何将两个以上的设计模式结合起来成为新的设计模式(例如著名的MVC模式),作者称其为复合设计模式(这是作者自创的名称,并非四人组的标准名词),第13章介绍如何进一步学习设计模式,如何发觉新的设计...
6命令模式封装调用 7适配器模式与外观模式随遇模式 8模板方法模式封装算法 9选代器与组合模式管理良好的集合 10状态模式事物的状态 11代理模式控制对象访问 12复合模式模式中的模型 ...
凯度厨房设备说明书
凯度厨房设备说明书
在法国贝宁的Bohicon和Hilla-Condji汽车站出售的烤羊肉Tchachanga的微生物质量根据法国标准进行了评估(DGAL,2000年)。 分析显示,波希克州(3.96×108 cfu / g)和Hilla-Condji(5.51×108 cfu / g)中记录的平均...
凯度厨房设备说明书
凯度厨房设备说明书
完整英文版 IEC 60335-2-6:2018 Household and similar electrical appliances - Safety - Part 2-6:Particular requirements for stationary cooking ranges, hobs, ovens and similar appliances(家用和类似...
Zojirushi象印品牌说明书