Command命令模式(行为型模式)
Command模式
问题:
实体对象与行为操作之间的耦合关系
动机:
在软件构建过程中,行为请求者与行为实现者通常呈现一种紧耦合。但
在某些场合---比如需要对行为进行“记录、撤销/重做、事务”等处理
,这种无法抵御变化的紧耦合是不合适的。
在这种情况下,如何将行为请求者与行为实现者解耦?将一组行为抽象
为对象,可以实现二者之间的松耦合。
意图:
将一个请求封装为一个对象,从而使你可用不同的请求对客户(行为的
请求者)进行参数化,对请求排队或记录请求日志,以及支持可撤销的
操作。
demo:
class Application
{
public void Show()
{
Document d = new Document();
d.ShowText();
Graphics g = new Graphics()
g.ShowGraphics();
}
}
class Document
{
public void ShowText(){}
}
class Graphics
{
public void ShowGraphics(){}
}
---
public abstract class Command
{
public void abstract Excute();
public void Undo();
public void Redo();
}
class Document : Command
{
public override void Excute(){}
}
class Graphics : Command
{
public ovrride void Excute(){}
}
class Application
{
ArrayList<Command> list;
public void Show()
{
foreach(Command c in list)
{ c.Excute();}
}
}
class Application
{
Stack<Command> stack;
public void Show()
{
}
public void Undo()
{
Command command = stack.pop();
}
public void Redo()
{
}
}
注:Command模式就是首先把行为抽象,再把具体行为封装为Command行
为,Command行为调用具体行为,这样客户就只与Command抽象发生依赖
。Command模式更倾向用于记录、撤销/重做、事务之类的操作。
public ICommand Command{
void Excute();
}
public Class DocumentCommand :ICommand
{
public void Excute()
{
Document d = new Document();
d.Do();
}
}
public Class GraphicsCommand :ICommand
{
}
public class Document
{
public void Do()
{}
}
public class Graphics
{
public void Foo()
{}
}
public class App
{
Stack<ICommand> stack;
public void test()
{
ICommand.Excute();
}
}
Command模式的几个要点
Command模式的根本目的在于将行为请求者与行为实现者解耦,在面向对
象语言中,常见的实现手段是将行为抽象为对象。
实现Command接口的具体命令对象ConcreteCommand有时候根据需要可能
会保存一些额外的状态信息。
通过使用Composite模式,可以将多个命令封装为一个复合命令
(MacroCommand)
Command模式与C#中的delegate有些类似。但者定义行为接口的规范有所
区别,command以面向对象中的接口-实现来定义行为接口规范,更严格,
更符合抽象原则;Delegate以涵数签名来定义行为接口规范,更灵活,
但抽象能力比较弱。
Delegate是一个更广的范畴,Command模式是Delegate的一种特例,也就
是可以抽象的特例。