java设计模式之命令模式
命令模式的定义:命令模式是对命令的封装,每一个命令都是一个操作:请求方发出请求要求执行一个操作;接收方收到请求,并执行操作。命令模式解耦了请求方 和接收方,请求方只需请求执行命令,不用关心命令怎么被接收、怎样操作以及是否被执行等。命令模式属于行为型设计模式。 在软件系统中,行为请求者与行为实现者通常是一种紧耦合关系,因为这样的实现简单明了。但紧耦合关系缺乏扩展性,在某些场合中,需要对行为 进行记录、撤销或者重做等处理时,只能修改源码。而命令模式通过在请求与实现之间引入一个抽象命令接口。解耦了请求与实现,并且中间件是抽象的, 它由不同的子类实现,因此具有扩展性。所以,命令模式的本质是解耦命令请求与处理。 命令模式的应用场景:
命令模式的UML类图:
? ? ? ?从上图可以看出,命令模式主要包含4个角色。
从命令模式的UML类图中,可以很清晰地看出,ICommand的出现就是作为Receiver和Invoker的中间件,解耦了彼此。 使用命令模式重构播放器控制条:假如我们开发一个播放器,播放器播放功能、拖动进度条功能、停止播放功能、暂停功能,我们在操作播发器的时候并不知道之间调用播放器 哪个功能,而是通过一个控制传达去传递指令给播放器内核,具体传达什么指令,会被封装成一个个按钮。那么每个按钮就相当于一条命令的封装。 用控制条实现了用户发送指令与播放器内核接收指令的解耦。下面来看代码,首先创建播放器内核类: public class GPlayer { void play() { System.out.println("正常播放"); } speed() { System.out.println("拖动进度条" stop() { System.out.println("停止播放" pause() { System.out.println("暂停播放"); } } 创建命令接口: interface IAction { execute(); } 创建播放指令类: class PlayAction implementsprivate GPlayer gplayer; public PlayAction(GPlayer gplayer) { this.gplayer = gplayer; } execute() { gplayer.play(); } } 创建暂停指令类: class PauseAction PauseAction(GPlayer gplayer) { execute() { gplayer.pause(); } } 创建拖动进度条类: class SpeedAction SpeedAction(GPlayer gplayer) { execute() { gplayer.speed(); } } 创建停止播放指令: class StopAction StopAction(GPlayer gplayer) { execute() { gplayer.stop(); } } 创建控制条controller类: Controller { private List<IAction> actions = new ArrayList<IAction>(); addAction(IAction action) { actions.add(action); } execute(IAction action) { action.execute(); } executes() { for (IAction action : actions) { action.execute(); } actions.clear(); } } 从上面代码来看,控制条可以执行单条命令,也可以批量执行多条命令。下面看客户端的测试代码: Test { static main(String[] args) { GPlayer player = new GPlayer(); Controller controller = Controller(); controller.execute( PlayAction(player)); controller.addAction( PauseAction(player)); controller.addAction( PlayAction(player)); controller.addAction( StopAction(player)); controller.addAction( SpeedAction(player)); controller.executes(); } } 由于控制条已经与播放器内核解耦了,以后如果想扩展新命令,只需要增加命令即可,控制条的结构无须改动。 命令模式的优点:
命令模式的缺点:
? (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |