您的位置:首页 > 编程语言 > Java开发

java23种设计模式(1)-命令模式

2017-12-07 18:27 501 查看

java23种设计模式(1)-命令模式

基本所有的程序员都听说过设计模式,可是有不小一波的新手对于设计模式不是很清楚哟!今天就来聊聊设计模式的命令模式。

所谓命令模式,我们首先来看一下什么是命令。通常情况下我们发出命令(信号),然后我们就看到了变化。这个具体是怎么变化的,我们作为命令的发出者很多时候不是很关心的。就像是老板一样只关心结果。

那我们来看看命令模式都有哪几部分组成!我们现在已电视为例子。首先,必须要有电视机也就是命令的接受者receiver。然后我们还必须要有一个遥控器,也就是有一个调度者invoker。当然了还少不了,我们的命令比如开机,比如播放等等一些列的,command。但是对于我们的程序员来说这些是不是够了呢好像不是很够!为什么因为如果命令没有一定的规范的话,那我们就应该定义一个接口,给出一定的规范。也就是相应的ICommand。那么最后我们应该也有一个客户端,也就是我们人,client。

那么模式应该是怎么样的呢?



talk is cheap ,show your code。


package com.bj.contract;

/**
* java 设计模式命令模式,命令接口,可以执行可以撤销!
* */
public interface Icommand {
void excute();
void undo();
}


package com.bj.contract.impl;

import com.bj.contract.Icommand;
import com.bj.recivier.TestReceiver;
/**
* 具体的命令,这个是用来解耦合的。持有接受者对象用来调用接受者来执行命令
* */
public class PlayCommand implements Icommand {
private TestReceiver testReceiver;

public PlayCommand(TestReceiver testReceiver) {
this.testReceiver = testReceiver;
}

@Override
public void excute() {
testReceiver.play();
}

@Override
public void undo() {
testReceiver.pause();
}
}


package com.bj.Invoker;

import com.bj.contract.Icommand;
import com.bj.contract.enums.CommandCache;

import java.util.HashMap;
import java.util.Map;
/**
* 命令的调度者,对客户端暴露接口。负责与客户端的交互,也就是命令的入口了
* */
public class TvInvoker {
private Map<String,Icommand> commandMap = new HashMap<>();
private CommandCache commandEnum;
//初始化,b把所有而已执行的命令都缓存一遍,客户端只需要根据命令的key来执行命令就可以了
public void  init(){
commandEnum=new CommandCache();
commandEnum.init();
for(Object key : commandEnum.getCommandHashMap().keySet()){
commandMap.put(String.valueOf(key), (Icommand) commandEnum.getCommandHashMap().get(key));
}
}

public Icommand removeCommand(String key){
return commandMap.remove(key);
}

public void excute(){
for(String string : commandMap.keySet()){
commandMap.get(string).excute();
}
}
public void excuteTCommadn(String key){
commandMap.get(key).excute();
}
public void undo(){
System.out.println("\"undo\" = " + "undo");
}

}


package com.bj.recivier;

/**
* 真正的命令接受者。所有的命令都有它执行。
* */
public class TestReceiver {
public void play(){
System.out.println("播放!");
}
public void pause(){
System.out.printf("暂停!");
}
}


package com.bj.contract.enums;

import com.bj.contract.Icommand;
import com.bj.contract.impl.PlayCommand;
import com.bj.recivier.TestReceiver;
import lombok.Data;

import java.util.HashMap;

/**
* 命令缓存,这里没有的命令不应该被执行!
* */
@Data
public class CommandCache<T extends Icommand> {

private HashMap<String,T> commandHashMap = new HashMap<String,T>();
public void init(){
commandHashMap.put("play", (T) new PlayCommand(new TestReceiver()));
}

}


package com.bj.example;

import com.bj.Invoker.TvInvoker;
import com.bj.contract.Icommand;
import com.bj.recivier.TestReceiver;
/**
* 测试命令模式
* */
public class CommandExample {
public static void main(String[] args) {
af53

TestReceiver testReceiver = new TestReceiver();
TvInvoker tvInvoker = new TvInvoker();
tvInvoker.init();
//        tvInvoker.excute();
tvInvoker.excuteTCommadn("play");

}
}


代码看完了,那么现在问题来了,这个设计模式的优点是什么?

松耦合,客户端和接受者之间已经解耦合完毕了。

动态控制简单,命令封装好以后队列化和日志就方便了。

扩展性非常好,因为前面的解耦合

说完了优点,再来说说应用场景

原子事务,因为可以回退。

状态条

导航

最后附上自己的GitHub地址:

https://github.com/yunzhifei/designPatterns.git
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: