问题描述:在许多的业务场景中,都有使用 if-else 来判断做出相应的计算,但是同级的大量 if-else 代码可读性、可维护性差,是一种面向过程的编程思想。使用策略模式 + 简单工厂模式实现 if-else 效果,使代码的可读性,可扩展性提高。
策略模式 + 简单工厂模式的实际用例
需求: 如果账号是超级管理员,返回状态码为1;是普通管理员返回状态码2;是考生返回状态码3
工厂模式调用不同的策略
/**
* @Author Snail
* @Describe 使用简单工厂方法模式替代大量的同级if-else
* 需求: 如果账号是超级管理员,返回状态码为1;是普通管理员返回状态码2;是考生返回状态码3
* @CreateTime 2020/1/17
*/
public class SimpleFactoryAndStrategy {
public static void main(String[] args) {
Integer userInteger;
String user = "admin";
//面向过程的写法
if ("supperAdmin".equals(user)) {
userInteger = 1;
} else if ("admin".equals(user)) {
userInteger =2;
}else if ("admin".equals(user)) {
userInteger =3;
}
//面向对象的写法
//饿汉式加展
userInteger = HungerSimpleFactory.getInstance().getReturn(user).doSomethingAndReturn();
System.out.println(userInteger + " and do something");
//懒汉式加展
userInteger=LazySimpleFactory.getInstance().getReturn(user).doSomethingAndReturn();
System.out.println(userInteger);
}
}
class HungerSimpleFactory {
//静态成员变量的线程安全由jvm初始化来保证
private static HungerSimpleFactory hungerSimpleFactory=new HungerSimpleFactory();
private static Map<String, StrategyItf> USER_MAP = new HashMap<>();
static {
USER_MAP.put("supperAdmin", new SupperAdmin());
USER_MAP.put("admin", new Admin());
USER_MAP.put("examinee", new Examinee());
}
//私有化,避免外部通过构造器初始化
private HungerSimpleFactory() {
}
public static HungerSimpleFactory getInstance() {
return hungerSimpleFactory;
}
StrategyItf getReturn(String user) {
return USER_MAP.get(user);
}
}
//懒加载方式,调用方法时才加载对应的数据
class LazySimpleFactory {
private static volatile LazySimpleFactory LAZY_SIMPLE_FACTORY;
private static Map<String, StrategyItf> USER_MAP;
private LazySimpleFactory() {
}
public static LazySimpleFactory getInstance() {
if (LAZY_SIMPLE_FACTORY == null) {
synchronized (LazySimpleFactory.class) {
if (LAZY_SIMPLE_FACTORY == null) {
LAZY_SIMPLE_FACTORY = new LazySimpleFactory();
USER_MAP=new HashMap<>();
USER_MAP.put("supperAdmin", new SupperAdmin());
USER_MAP.put("admin", new Admin());
USER_MAP.put("examinee", new Examinee());
}
}
}
return LAZY_SIMPLE_FACTORY;
}
public StrategyItf getReturn(String user) {
return USER_MAP.get(user);
}
}
策略模式接口及实现类
优点:
- 策略的实现可以自由切换
- 扩展性良好,满足开闭原则
- 增加一个策略,就多增加一个类就好了
缺点:
- 策略类的数量增多
- 每一个策略都是一个类,复用的可能性很小、类数量增多
- 所有的策略类都需要对外暴露,上层模块必须知道有哪些策略,然后才能决定使用哪一个策略
interface StrategyItf {
Integer doSomethingAndReturn();
}
class SupperAdmin implements StrategyItf {
@Override
public Integer doSomethingAndReturn() {
return 1;
}
}
class Admin implements StrategyItf {
@Override
public Integer doSomethingAndReturn() {
return 2;
}
}
class Examinee implements StrategyItf {
@Override
public Integer doSomethingAndReturn() {
return 3;
}
}