设计模式学习--命令模式(command)

前言

已经从事软件开发很多年了,但是感觉自己在技术上也没有显著地进步。所以就想学一些软件设计提升自己,以前也曾粗粗的翻过《Design Pattern》、《java模式》之类的书籍,当时除了对面向接口编程、开闭原则等概念性的知识、及一些简单的模式(工厂、单例)有一点感觉之外,对大部分模式的使用场景都处于一个比较初级的阶段。 这次准备重学设计模式,且准备采用精学的方式、宁可慢一点也要把每个模式吃透。使用的书籍选用 《Head First Design Pattern》、《敏捷软件开发 原则、模式、实践》,相对《Design Pattern》更适合初学者学习。

为什么使用设计模式

对任何设计都可以凭主观(对设计很难做出客观评价)判断得出它是一个好的设计,还是一个坏的设计。使用设计模式是为了避免坏的设计。
坏设计的症状:
  僵化性(Rigidity):设计难以改变。
  脆弱性(Fragility):设计易于遭到破坏。
  牢固性(Immobility):设计难以重用。
  粘滞性(Viscosity):难以做正确的事情。
  不必要的复杂性(Needless Complexity):过分设计。
  不必要的重复(Needless Repetition):过多的重复。
  晦涩性(Opacity):混乱的表达。

命令模式(command)

模式意图

1 命令模式的目标是对请假调用者,和请求接受者进行解耦(如图中Invoker和Receiver没有关联)
2.将“请求”封装成对象,以便使用不同的请求、队列、日志参数化其他对象。(“请求”是指预先定义的操作,就是请求所对应的操作,而非像servlet中request由客户出发的请求)


代码实例(简单遥控器)

public class RemoteControlTest{ //RemoteControlTest就是命令模式的client

	public static void public static void main(String[] args) {
		SimpleRemoteControl remote = new SimpleRemoteControl();//是调用者
		Light light = new Light();//接受者
		LightCommand lightOn = new LightCommand(light);//创建一个命令,将接受者传给他

		remote.setCommand(lightOn);//把命令传给调用者
		remote.buttonWasPressed();
	}
}

撤销方式实现

要实现撤销方式需完成以下步骤
1 在command接口中添加undo方法
2 在command实现类实现undo方法
3 在调用者类中存放一个 undoCommand 变量,在每次执行commond.excute方法的时候设置这个undoCommand属性。
其它类型撤销:
连续撤销:需要在Invoker中放一个stack uncommand即可。
带状态撤销:早command实现类中记录一个状态 ,excucete方法中预先记录一下执前的状态(headfirst P221)

宏命令:

1.宏命令也是一个具体command实。
2.在这个command存放着一个命令集合。
3.excute方法执行时执行命令集合中所有的command。

其它应用场合:

1.事务操作:
因为命令模式支持撤销、及宏命令,所以只要在宏命令撤销方法中撤销所有操作即能实现实务回滚。(当然还需要对excute做一些异常处理)
2.日志系统 headfirst P229
在具体command中添加 load 和 store 方法(还没细想)。

遇到的问题:

1.从简单遥控器实力中看到Invoker(SimpleRemoteControl)是在是在client(RemoteControlTest)中初始化的,也就是说client也对invoker有依赖关系,但为什么在uml图中为什么没有画上呢?

我的理解:
根据问题也 翻阅了一些资料,在《java设计模式》中client 和 Invoker是有这条连线的。那为什么大部分的资料都没有此连线呢。
命令模式中的client的主要工作是负责装配各类command。
client和Invoker的之间可能存在多种关系。
1. client 依赖 invoker(如RemoteControlTest的例子)
2. 没有依赖(如以下代码,client只负责装配所有的命令,和 invoker 并没有任何依赖关系)。
CommandList  list = client.getAllCommand();// 装配所有的命令
invoker.setCommandList( list);//装在所有命令
invoker.excuteCommand(1);//执行命令











  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值