命令模式——HeadFirst设计模式学习笔记
Posted HectorHou
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了命令模式——HeadFirst设计模式学习笔记相关的知识,希望对你有一定的参考价值。
命令模式:将“请求”封装成对象,以便使用不同的请求、日志、队列等来参数化其他对象。命令模式也支持撤销操作。
设计原则:
- 把方法的调用封装起来,调用此对象不需要知道它内部具体是如何运行的,只需要知道包装成型的方法
- 命令模式的本质是对命令进行封装,将发出命令的责任和执行命令的责任分割开
- 将“动作请求者”从“动作执行者”中解耦,即将发出请求的对象和接受并执行请求的对象分离开来。两者通过命令对象沟通
- 命令模式的关键在于引入了抽象命令接口,且发送者针对抽象命令接口编程,只有实现了抽象命令接口的具体命令才能与接收者相关联
特点:
- 对象只知道通过接口暴露出execute()方法,当此方法调用时,接受者执行具体的动作。对象不知道那个接受者执行了什么动作,只知道操作进行了
NoCommand对象:execute()方法为空的对象,即不执行任何操作的对象。客户端处理null操作时交给空对象,而无需做if(command != null)操作。
撤销操作:在管理一组操作对象的对象中可以添加一个上一个操作的对象引用,用于追踪最后调用的命令,并通过命令的undo()方法实现撤销。同样在操作命令对象中也可添加局部变量记录上一个状态以实现undo()方法。
可使用堆栈记录操作过程中的每一个命令,实现多次撤销
宏命令:同时执行多个命令,软编码,传入命令数组,动态决定哪些命令
日志请求:使用命令模式的记录日志,我们可以将上个检查点之后的操作都记录下来,如果系统出现问题,从检查点开始执行命令
队列请求:把一组命令放到队列(先进先出)中,线程从队列中一个一个删除命令,然后调用它的excecute()方法。
类图:
Command:定义命令的接口,声明执行的方法。
ConcreteCommand:命令接口实现对象,通常会持有接收者,并调用接收者的功能来完成命令要执行的操作。(组合方式)
Receiver:接收者,真正执行命令的对象。任何类都可能成为一个接收者,只要它能够实现命令要求实现的相应功能。
Invoker:要求命令对象执行请求,通常会持有命令对象,可以持有很多的命令对象。
Client:创建具体的命令对象,并且设置命令对象的接收者。真正使用命令的客户端是从Invoker来触发执行。
举例:
使用命令模式实现遥控器,遥控器上的不同按钮控制电灯的开关及亮度、天花板风扇的开关及转速等,支持撤销
1、命令接口:Command
1 public interface Command { 2 public void execute(); 3 }
2、对Receiver(灯)实现开关命令
1 public class LightOnCommand implements Command { 2 Light light; 3 public LightOnCommand(Light light) { 4 this.light = light; 5 } 6 public void execute() { 7 light.on(); 8 } 9 } 10 11 public class LightOffCommand implements Command { 12 Light light; 13 public LightOffCommand(Light light) { 14 this.light = light; 15 } 16 public void execute() { 17 light.off(); 18 } 19 }
3、实现Invoker控制
1 public class SimpleRemoteControl { 2 Command slot; 3 public SimpleRemoteControl() {} 4 public void setCommand(Command command) { 5 slot = command; 6 } 7 public void buttonWasPressed() { 8 slot.execute(); 9 } 10 }
4、Client使用Invoker控制器
1 public class RemoteControlTest { 2 public static void main(String[] args) { 3 SimpleRemoteControl remote = new SimpleRemoteControl(); 4 Light light = new Light(); 5 LightOnCommand lightOn = new LightOnCommand(light); 6 remote.setCommand(lightOn); 7 remote.buttonWasPressed(); 8 } 9 }
以上是关于命令模式——HeadFirst设计模式学习笔记的主要内容,如果未能解决你的问题,请参考以下文章