- 浏览: 98325 次
- 性别:
- 来自: 深圳
文章分类
最新评论
Command(CoR)模式也叫命令模式,是由GoF提出的23种软件设计模式的一种。本文介绍设计模式中的(Command)模式的概念,用法,并用Command模式给出了一个简单的execute/undo实现。
Command模式的概念
Command模式是行为模式之一,Command模式通过被称为Command的类封装了对目标对象的调用行为以及调用参数。Command模式的应用场景
在面向对象的程序设计中,一个对象调用另一个对象,一般情况下的调用过程是:创建目标对象实例;设置调用参数;调用目标对象的方法。但在有些情况下有必要使用一个专门的类对这种调用过程加以封装,我们把这种专门的类称作command类。
- 整个调用过程比较繁杂,或者存在多处这种调用。这时,使用Command类对该调用加以封装,便于功能的再利用。
- 调用前后需要对调用参数进行某些处理。
- 调用前后需要进行某些额外处理,比如日志,缓存,记录历史操作等。
一般来说,Command模式通常可应用到以下场景:
Multi-level undo(多级undo操作)
如果系统需要实现多级回退操作,这时如果所有用户的操作都以command对象的形式实现,系统可以简单地用stack来保存最近执行的命令,如果用户需要执行undo操作,系统只需简单地popup一个最近的command对象然后执行它的undo()方法既可。
Transactional behavior(原子事务行为)
借助command模式,可以简单地实现一个具有原子事务的行为。当一个事务失败时,往往需要回退到执行前的状态,可以借助command对象保存这种状态,简单地处理回退操作。
Progress bars(状态条)
假如系统需要按顺序执行一系列的命令操作,如果每个command对象都提供一个getEstimatedDuration()方法,那么系统可以简单地评估执行状态并显示出合适的状态条。
Wizards(导航)
通常一个使用多个wizard页面来共同完成一个简单动作。一个自然的方法是使用一个command对象来封装wizard过程,该command对象在第一个wizard页面显示时被创建,每个wizard页面接收用户输入并设置到该command对象中,当最后一个wizard页面用户按下 “Finish”按钮时,可以简单地触发一个事件调用execute()方法执行整个动作。通过这种方法,command类不包含任何跟用户界面有关的代码,可以分离用户界面与具体的处理逻辑。
GUI buttons and menu items(GUI按钮与菜单条等等)
Swing系统里,用户可以通过工具条按钮,菜单按钮执行命令,可以用command对象来封装命令的执行。
Thread pools(线程池)
通常一个典型的线程池实现类可能有一个名为addTask()的public方法,用来添加一项工作任务到任务队列中。该任务队列中的所有任务可以用command对象来封装,通常这些command对象会实现一个通用的接口比如java.lang.Runnable。
Macro recording(宏纪录)
可以用command对象来封装用户的一个操作,这样系统可以简单地通过队列保存一系列的command对象的状态就可以记录用户的连续操作。这样通过执行队列中的command对象,就可以完成“Play back”操作了。
Networking
通过网络发送command命令到其他机器上运行。
Parallel Processing(并发处理)
当一个调用共享某个资源并被多个线程并发处理时。
等等
Command模式的结构
Command
Command抽象类。
ConcreteCommand
Command的具体实现类。
Receiver
需要被调用的目标对象。
Invorker
通过Invorker执行Command对象。
Client
调用方。
Command模式的应用范例
下面,我们使用Command模式实现一个简单的execute/undo操作。在该范例中,我们有一个简单的操作:对字符串做append操作,这个操作由Receiver类实现;另外,我们需要记录操作历史,并能简单加以回退(undo),所以我们采用Command模式实现。
文件一览:
Client
测试类
Command
Command抽象类
UndoableCommand
支持undo操作的Command抽象类,该类是Command类的子类
ConcreteCommand
具体的UndoableCommand实现类,该类继承UndoableCommand类,所以支持undo操作
CommandManager
Command管理类。该类使用Stack来管理执行过的Command对象,并提供executeCommand()与undoCommand()方法
Receiver
执行任务的目标类
Invoker
这个类在我们的例里没有被用到,但我们仍给出了它的一个参考实现,不过用注释表示它不可用
代码:
import java.util.Stack;
public class Client {
/**
* Test Command Pattern
*
*/
public static void main(String[] args) {
CommandManager commandMgr = new CommandManager();
Receiver receiver = new Receiver();
System.out.println("--- execute command ---");
Command commandAaa = new ConcreteCommand(receiver, "aaa");
commandMgr.executeCommand(commandAaa);
Command commandBbb = new ConcreteCommand(receiver, "bbb");
commandMgr.executeCommand(commandBbb);
Command commandCcc = new ConcreteCommand(receiver, "ccc");
commandMgr.executeCommand(commandCcc);
Command commandDdd = new ConcreteCommand(receiver, "ddd");
commandMgr.executeCommand(commandDdd);
System.out.println(receiver.getData());
System.out.println("-- undo ---");
commandMgr.undoCommand();
commandMgr.undoCommand();
System.out.println(receiver.getData());
}
}
/**
* Command
* abstract command class
*
*/
abstract class Command {
protected Receiver receiver;
protected String param;
public Command(Receiver receiver, String expr) {
this.receiver = receiver;
this.param = expr;
}
abstract public void execute();
}
/**
* UndoableCommand
* abstract undo supportable command class which extends from Command class
*
*/
abstract class UndoableCommand extends Command {
public UndoableCommand(Receiver receiver, String expr) {
super(receiver, expr);
}
abstract public void undo();
}
/**
* ConcreteCommand
* concrete command class which extends from UndoableCommand
*
*/
class ConcreteCommand extends UndoableCommand {
private String previousData = null;
public ConcreteCommand(Receiver receiver, String expr) {
super(receiver, expr);
}
@Override
public void execute() {
previousData = receiver.getData();
receiver.append(this.param);
}
@Override
public void undo() {
receiver.setData(previousData);
}
}
/**
* CommandManager
* Command Manager class which stack the exe
*
*/
class CommandManager {
private Stack commandStack = new Stack();
public void executeCommand(Command cmd) {
cmd.execute();
if (cmd instanceof UndoableCommand) {
commandStack.push(cmd);
}
}
public void undoCommand() {
if (commandStack.size() > 0) {
UndoableCommand cmd = (UndoableCommand) commandStack.pop();
cmd.undo();
} else {
throw new UnsupportedOperationException("");
}
}
}
/**
* Receiver
* target object
*
*/
class Receiver {
private String data = "";
public void append(String expr) {
data += expr;
}
public String getData() {
return data;
}
public void setData(String data) {
this.data = data;
}
}
/**
class Invoker {
private Command command;
public void setCommand(Command command) {
this.command = command;
}
public void executeCommand() {
command.execute();
}
}
*/
public class Client {
/**
* Test Command Pattern
*
*/
public static void main(String[] args) {
CommandManager commandMgr = new CommandManager();
Receiver receiver = new Receiver();
System.out.println("--- execute command ---");
Command commandAaa = new ConcreteCommand(receiver, "aaa");
commandMgr.executeCommand(commandAaa);
Command commandBbb = new ConcreteCommand(receiver, "bbb");
commandMgr.executeCommand(commandBbb);
Command commandCcc = new ConcreteCommand(receiver, "ccc");
commandMgr.executeCommand(commandCcc);
Command commandDdd = new ConcreteCommand(receiver, "ddd");
commandMgr.executeCommand(commandDdd);
System.out.println(receiver.getData());
System.out.println("-- undo ---");
commandMgr.undoCommand();
commandMgr.undoCommand();
System.out.println(receiver.getData());
}
}
/**
* Command
* abstract command class
*
*/
abstract class Command {
protected Receiver receiver;
protected String param;
public Command(Receiver receiver, String expr) {
this.receiver = receiver;
this.param = expr;
}
abstract public void execute();
}
/**
* UndoableCommand
* abstract undo supportable command class which extends from Command class
*
*/
abstract class UndoableCommand extends Command {
public UndoableCommand(Receiver receiver, String expr) {
super(receiver, expr);
}
abstract public void undo();
}
/**
* ConcreteCommand
* concrete command class which extends from UndoableCommand
*
*/
class ConcreteCommand extends UndoableCommand {
private String previousData = null;
public ConcreteCommand(Receiver receiver, String expr) {
super(receiver, expr);
}
@Override
public void execute() {
previousData = receiver.getData();
receiver.append(this.param);
}
@Override
public void undo() {
receiver.setData(previousData);
}
}
/**
* CommandManager
* Command Manager class which stack the exe
*
*/
class CommandManager {
private Stack commandStack = new Stack();
public void executeCommand(Command cmd) {
cmd.execute();
if (cmd instanceof UndoableCommand) {
commandStack.push(cmd);
}
}
public void undoCommand() {
if (commandStack.size() > 0) {
UndoableCommand cmd = (UndoableCommand) commandStack.pop();
cmd.undo();
} else {
throw new UnsupportedOperationException("");
}
}
}
/**
* Receiver
* target object
*
*/
class Receiver {
private String data = "";
public void append(String expr) {
data += expr;
}
public String getData() {
return data;
}
public void setData(String data) {
this.data = data;
}
}
/**
class Invoker {
private Command command;
public void setCommand(Command command) {
this.command = command;
}
public void executeCommand() {
command.execute();
}
}
*/
执行Client,输出结果:
C:\Command>javac *.java
C:\Command>java Client
--- execute command ---
aaabbbcccddd
-- undo ---
aaabbb
C:\Command>
我们可以看到,使用Command模式非常简单地就实现了undo操作。C:\Command>java Client
--- execute command ---
aaabbbcccddd
-- undo ---
aaabbb
C:\Command>
发表评论
-
设计模式之 State - 状态模式
2010-12-18 16:49 1071State模式也叫状态模式,是由GoF提出的23种软件设计模式 ... -
设计模式之 Strategy - 策略模式
2010-12-18 16:46 1343Strategy模式也叫策略模 ... -
设计模式之 Visitor - 访问者模式
2010-12-18 16:45 1443Visitor模式也叫访问者 ... -
设计模式之 Template Method - 模板方法模式
2010-12-18 16:41 1562Template Method模式也叫模板方法模式,是由G ... -
设计模式之 Observer - 观察者模式
2010-12-18 16:33 1371Observer模式也叫观察者 ... -
设计模式之 Memento - 备忘录模式
2010-12-18 16:31 1043Memento模式也叫备忘录 ... -
设计模式之 Mediator - 中介者模式
2010-12-18 16:29 1103Mediator模式也叫中介者模式,是由GoF提出的23种软件 ... -
设计模式之 Iterator - 迭代模式
2010-12-18 16:27 1162Iterator模式也叫迭代模式,是由GoF提出的23种设 ... -
设计模式之 Interpreter - 解释器模式
2010-12-18 16:23 983Interpreter模式也叫解释器模式,是由GoF提出的 ... -
设计模式之 Chain of Responsibility - 职责链模式
2010-12-18 16:18 1191Chain of Responsibility(CoR)模 ... -
设计模式之 Proxy - 代理模式
2010-12-16 23:45 1040Proxy模式也叫代理模式,是由GoF提出的23种软件设计 ... -
设计模式之 Flyweight - 享元模式
2010-12-16 23:42 1031Flyweight模式也叫享元模式,是由GoF提出的23种 ... -
设计模式之 Facade - 外观模式
2010-12-16 23:41 991Facade模式也叫外观模式 ... -
设计模式之 Singleton - 单态模式
2010-11-26 11:58 845Singleton模式也叫单态模式,是由GoF提出的2 ... -
设计模式之 Decorator - 装饰模式
2010-11-25 23:48 802装饰模式,The Decorator Pattern atta ... -
设计模式之 Composite - 组合模式
2010-11-25 23:35 1448Composite模式也叫组合 ... -
设计模式之 Bridge - 桥接模式
2010-11-25 23:08 1006Bridge模式也叫桥接模式,是由GoF提出的23种软件设计模 ... -
设计模式之 Adapter - 适配器模式
2010-11-25 22:58 904Adapter模式也叫适配器模式,是由GoF提出的23种设 ... -
设计模式之Prototype - 原型模式
2010-11-25 22:14 1123Prototype模式也叫原型模式,是由GoF提出的23种设计 ... -
设计模式之 Builder - 建造者模式
2010-11-18 23:51 1034Builder模式也叫建造者模式或者生成器模式,是由GoF ...
相关推荐
有关设计模式里边的命令模式,内含ppt、源代码及结果、word整理。在此以供大家学习交流。
设计模式C++学习之命令模式(Command)
c++设计模式-行为型模式-命令模式;qt工程 ;c++简单源码; 命令(Command)模式的定义如下:将一个请求封装为一个对象,使发出请求的责任和执行请求的责任分割开。这样两者之间通过命令对象进行沟通,这样方便将...
命令模式,将一个请求封装为一个对象,从而使你可用不同的请求对客户进行参数化;对请求排队或记录请求日志,以及支持可撤消的操作。
C++设计模式代码资源23_Command_命令模式.zip
Head First 设计模式 (六) 命令模式(Command pattern) C++实现
命令模式(Command) 用意:把一个请求封装到一个对象中,把发出命令和执行命令的责任分开,委派给不同的对象实现。
C#面向对象设计模式纵横谈(15):(行为型模式) Command 命令模式
将一个请求封装为一个对象,从而使你可用不同的请求对客户进行参数化;对请求排队或记录请求日志,以及支持可取消的操作。
Command设计模式ppt 代码示例 设计模式 Command ppt 代码实例 撤销重做实例
命令模式 Command 设计模式 若理解有问题,还请大S指教。
C++设计模式课件23_Command_命令模式.pdf
<!-- TOC --> - 23种设计模式 - 工厂方法模式(Factory Method) - 抽象工厂模式(Abstract ... - 命令模式(Command) - 解释器模式(Interpreter) - 迭代器模式(Iterator) - 备忘录模式(Memento) - 状态模式(S
值得学习的命令模式代码,会让你有一定的收获,并有详细的说明和代码解析。
1.1 什么是设计模式 2 1.2 Smalltalk MVC 中的设计模式 3 1.3 描述设计模式 4 1.4 设计模式的编目 5 1.5 组织编目 7 1.6 设计模式怎样解决设计问题 8 1.6.1 寻找合适的对象 8 1.6.2 决定对象的粒度 9 1.6.3 指定对象...
C#面向对象设计模式纵横谈(15):(行为型模式) Command 命令模式 (Level 300)
3.1 抽象命令(Command):定义命令的接口,声明执行的方法。 3.2 具体命令(ConcreteCommand):具体命令,实现要执行的方法,它通常是“虚”的实现;通常会有接收者,并调用接收者的功能来完成命令要
设计模式(18)-Command Pattern 168 一、 命令(Command)模式 168 二、 命令模式的结构 168 三、 命令模式的示意性源代码 169 四、 玉帝传美猴王上天 172 五、 命令模式的实现 172 六、 命令模式的实际应用案例 ...
命令模式是一种行为设计模式,它将一个请求封装成一个对象,从而允许用户根据不同的请求对客户进行参数化;同时,它也支持撤销操作。 命令模式的核心在于通过命令对象实现调用操作和实现操作的解耦。这种模式通常...
设计模式-适配器-工厂-命令-备忘录Java中的Adapter&Factory&Command&Memento设计模式GoodHealth Fitness Corporation 是一家大型健身俱乐部。 它提供最先进的设备供其成员使用。 公司维护一个会员系统,用于记录会员...