策略模式,重构if-else
最近完成了我们公司的公众号开发,在微信消息路由选择的时候一开始都是用if-else 来判断,后面if-else月写越多显得十分的乱。在网上简单查了一下解决方法,果然有不少干货,感觉最经典最简洁的还是使用策略模式来重构过多的if-else 选择。
首先我们新建一个interface
public interface InnerCommand {
void process(String msg);
}
然后把每一个if逻辑都单独抽取到一个类里面如
/**
* @author lee.
* @date 2019/5/24 15:53
*/
@Service
public class PrintAdminCommand implements InnerCommand {
@Override
public void process(String msg) {
System.out.println("PrintAdminCommand");
}
}
这里就不一一列举了。
然后我们这里新建一个enum CommonCode
/**
* @author lee.
* @date 2019/5/24 15:51
*/
public enum CommonCode { USER("user", "用户", "com.yumstone.invoiceapply.Command.impl.PrintUserCommand"),
ADMIN("admin", "管理员", "com.yumstone.invoiceapply.Command.impl.PrintAdminCommand");
private String code;
private String desc;
private String clazz;
private static final Map<String, String> classes = new HashMap<String, String>(); static {
for (CommonCode refer : CommonCode.values()) {
classes.put(refer.getCode(), refer.getClazz());
}
} CommonCode(String code, String desc, String clazz) {
this.code = code;
this.desc = desc;
this.clazz = clazz;
} public static Map<String, String> getAllClazz() {
return classes;
}
public static String getDescByCode(int code) {
return classes.get(code);
}
public String getCode() {
return code;
}
public void setCode(String code) {
this.code = code;
}
public String getDesc() {
return desc;
}
public void setDesc(String desc) {
this.desc = desc;
}
public String getClazz() {
return clazz;
}
public void setClazz(String clazz) {
this.clazz = clazz;
}
}
这里我们可以看到枚举类里面有一个静态代码块在程序一开始执行的的时候就会把类和对应的code 加载到内存中。
再然后我们新建一个组件处理根据不同的code获取不同的处理类,
/**
* @author lee.
* @date 2019/5/24 15:59
*/
@Component
public class InnerCommandContext {
@Autowired
ApplicationContext applicationContext; public InnerCommand getInstance(String command) {
//getAllClazz
Map<String, String> allClazz = CommonCode.getAllClazz();
String clazz = allClazz.get(command);
InnerCommand innerCommand = null;
try {
if (clazz==null||clazz.length()==0) {
clazz = PrintAdminCommand.class.getName() ;
}
innerCommand = (InnerCommand)applicationContext.getBean(Class.forName(clazz));
} catch (Exception e) {
e.printStackTrace();
}
return innerCommand;
}
}
这里我们可以看到获取的类是通过反射在spring容器里面找到的。好了到这里我们的准备工作就做完了最后写我们的逻辑部分。
/**
* @author lee.
* @date 2019/5/24 16:06
*/
@RestController
public class TextController {
@Autowired
InnerCommandContext innerCommandContext;
@RequestMapping("text")
public String test(@RequestParam String name){
InnerCommand innerCommand = innerCommandContext.getInstance(name);
innerCommand.process(name);
return "ok" ;
}
}
是不是特别简洁 原来可能很多if-else 的判断现在被优化成了两行代码
InnerCommand innerCommand = innerCommandContext.getInstance(name);
innerCommand.process(name);
总结程序在启动的时候会把所有的逻辑类的类名加载到内存中,然后通过code找到所需的类型通过反射构建出来,最后就可以执行所需要处理的业务了,在新增一个逻辑只需要新增一个 InnerCommand 的实现类并且添加到枚举类里面去就行了。然后就可以通过该类型的code来获取。
策略模式,重构if-else的更多相关文章
- 使用策略模式重构switch case 代码
目录 1.背景 2.案例 3.switch…case…方式实现 4.switch…case…带来的问题 5.使用策略模式重构switch…case…代码 6.总结 1.背景 之前在看<重构 ...
- java设计模式--策略模式
策略模式属于对象的行为模式.其用意是针对一组算法,将每一个算法封装到具有共同接口的独立的类中,从而使得它们可以相互替换.策略模式使得算法可以在不影响到客户端的情况下发生变化. 本文地址:http:// ...
- 理解javascript中的策略模式
理解javascript中的策略模式 策略模式的定义是:定义一系列的算法,把它们一个个封装起来,并且使它们可以相互替换. 使用策略模式的优点如下: 优点:1. 策略模式利用组合,委托等技术和思想,有效 ...
- JavaScript设计模式与开发实践 - 策略模式
引言 本文摘自<JavaScript设计模式与开发实践> 在现实中,很多时候也有多种途径到达同一个目的地.比如我们要去某个地方旅游,可以根据具体的实际情况来选择出行的线路. 如果没有时间但 ...
- 《JavaScript设计模式与开发实践》读书笔记之策略模式
1.策略模式 定义一系列算法,把它们一个个封装起来,并且使它们可以相互替换 1.1 传统实现 根据工资基数和年底绩效来发送年终奖 var calculateBonus= function (perfo ...
- JavaScript设计模式_02_策略模式
在程序设计中,我们常常遇到这种情况,要实现某一个功能我们有很多种算法可以实现.这些算法灵活多样,而且可以随意互相替换.这种解决方案就是所谓的策略模式. /* * pre:策略模式 * 示例:公司计算奖 ...
- javascript设计模式——策略模式
前面的话 在程序设计中,常常遇到类似的情况,要实现某一个功能有多种方案可以选择.比如一个压缩文件的程序,既可以选择zip算法,也可以选择gzip算法.这些算法灵活多样,而且可以随意互相替换.这种解决方 ...
- JavaScript设计模式之策略模式
所谓"条条道路通罗马",在现实中,为达到某种目的往往不是只有一种方法.比如挣钱养家:可以做点小生意,可以打分工,甚至还可以是偷.抢.赌等等各种手段.在程序语言设计中,也会遇到这种类 ...
- JavaScript设计模式 Item 7 --策略模式Strategy
1.策略模式的定义 何为策略?比如我们要去某个地方旅游,可以根据具体的实际情况来选择出行的线路. 如果没有时间但是不在乎钱,可以选择坐飞机. 如果没有钱,可以选择坐大巴或者火车. 如果再穷一点,可以选 ...
- 《JavaScript设计模式与开发实践》-- 策略模式
详情个人博客:https://shengchangwei.github.io/js-shejimoshi-celue/ 策略模式 1.定义 策略模式:定义一系列的算法,把它们一个个封装起来,并且使它们 ...
随机推荐
- 【C语言】复合函数求值
例子:求复合函数F(G(X)),其中F(x)=|x-3|+|x+1|,函数G(x)=x^2-3x. 分析:从复合函数的结构可以看出,F函数的自变量为G函数的绝对值,可以将F函数和G函数作为独立的函数实 ...
- Tomcat配置过程
Tomcat的配置其实还是挺简单的,下面是在Myeclipse中配置 1.首先要在Tomcat官网下载,网址:http://tomcat.apache.org/,然后左侧会有Download,选择你要 ...
- vue 无法热替换/热更新
参考了小伙伴的解决办法: 1.https://blog.csdn.net/win7583362/article/details/65443291 虽然我并不是用对方的方法解决的. 依然还是建议大家打开 ...
- pycharm开发flask指定ip、端口无效
原因分析 是因为使用了pycharm的版本的问题.并不是flask框架本身的问题(不管你是如何设置的flask配置,通过加载config也好,还是通过run的时候传入形参也好,均不影响) 可以很明显的 ...
- 解决安装VMware Player出错,提示安装程序无法继续,microsoft runtime dll安装程序未能完成安装
方案一: 以兼容模式运行和管理员方式运行安装程序,右键点击安装文件选择属性,在弹出的面板中修改兼容性如下 方案二: 下载最近版的VMWare player安装包哈哈 方案三: 1.双击VMware P ...
- FreeRTOS学习笔记3:内核控制及开启调度器
内核控制函数API 应用层中不会用到taskYIELD() //任务切换.会自动切换当前就绪表里优先级最高的任务 临界区 //不能被打断的代码段任务中进入临界区任务中退出临界区中断服务进入临界区中断服 ...
- 吴裕雄 python 机器学习——数据预处理过滤式特征选取SelectPercentile模型
from sklearn.feature_selection import SelectPercentile,f_classif #数据预处理过滤式特征选取SelectPercentile模型 def ...
- React源码解析之React.Children.map()(五)
一,React.Children是什么? 是为了处理this.props.children(this.props.children表示所有组件的子节点)这个属性提供的工具,是顶层的api之一 二,Re ...
- TCP和UDP的一些注意事项
TCP的一些注意事项 1. tcp服务器一般情况下都需要绑定,否则客户端找不到这个服务器,更无法链接到服务器 2. tcp客户端一般不绑定,因为是主动链接服务器,所以只要确定好服务器的ip.port等 ...
- 每天进步一点点------SOPC的Avalon-MM IP核(四) KEY_LED IP定制
/********************************************************************************* * Company : * Eng ...