命令模式的理解和示例
一、是什么?作用
1. 命令模式 将“请求”封装成对象,以使用不同的请求队列或者日志来参数话其他对象,命令模式亦可以来支持撤销的操作
2. 将请求封装成命令对象,请求的具体执行由命令接收者执行;
作用:
命令发送者与命令执行者解耦;
每一个命令都是一个操作
3. 类图
Invoke(调用者): 调用者负责执行命令
Command(命令接口): 负责将操作封装成统一的方法
Concreatecommand(命令实现类): 负责将命令真正执行者的操作封装起来
Receiver(接受者): 命令的真正执行者
二、示例
代码场景: 厂商提供一个遥控器,遥控器有个按钮开关,需要你往这个遥控器上加不同的电器,如: 灯、风扇、空调、门
代码分析: 命令模式将电器的操作请求封装成对象
灯:命令的真正执行者
/** * 灯 (Receiver) 命令的真正执行者 */ public class Light { public void on() { System.out.println("开灯"); } public void off() { System.out.println("关灯"); } }
命令接口: 上面有个操作的按钮,当然你也可以添加其他操作,如: undo
/** * 命令接口 */ public interface Command { void execute(); }
将开灯这个请求封装成命令对象,如果有其他电器的操作,也可以封装成命令对象
/** * 开灯命令 (LinghtOnCommand )
*/
public class LinghtOnCommand implements Command {
private Light light; // 这里使用委托解耦
public LinghtOnCommand(Light light) { this.light = light; }
@Override
public void execute() { light.on(); }
}
(遥控器)命令调用者:将命令安装到遥控器上,同时提供按下按钮,执行该命令的操作
/** * 遥控器 * 命令调用者 invoke */ public class CommandController { private Command solt; public void setCommand(Command command) { solt = command; } /** * 遥控器 按钮按下 */ public void buttonWasPressed() { solt.execute(); } }
客户端调用:
/** * 测试客户端 */ public class MainClient { public static void main(String[] args) { CommandController commandController = new CommandController(); Light light = new Light(); LinghtOnCommand linghtOnCommand = new LinghtOnCommand(light); commandController.setCommand(linghtOnCommand); commandController.buttonWasPressed(); } }
// 控制台显示
开灯
三、总结
1.小结
- 命令模式将发出请求对象(CommandController )和执行请求对象解耦
- 调用命令对象的execute(), 会使得接受者的动作会被执行
- 命令模式也支持撤销,做法是实现一个undo命令,返回execute()被执行之前的状态
2. 命令模式的更多用途:
- 队列请求: 从队列中取出一个命令,调用它的execute(),等待调用完成,将命令对象丢弃,再取下一个命令
- 日志请求
- 事务: 撤销之前的操作
- 线程池
- 。。。