【策略模式】重构代码 - 记一次策略模式的运用

背景

小七最近看代码时发现了以前自己写的一个方法,伪代码如下:

private BigDecimal matchingAlgorithm(String type, BigDecimal totalAmount) {
    // 匹配算法
    // 个位,四舍五入
    if (TypeEnum.HALF_UP.getCode().equals(type)){
       
    }
    // 十位,向下取整
    else if (TypeEnum.ROUND_FLOOR.getCode().equals(type)){
       
    }
    // 十位,向上取整
    else if (TypeEnum.ROUND_HALF_EVEN.getCode().equals(type)){
       
    }
    return totalAmount;
}

功能很简单通过类型匹配不同的算法。这样写虽然功能实现了,但是想一想其实有更优雅的实现方式。那就是今天的主角策略模式了。

思考过程

同大多数其它模式一样,我们首先也需要抽象出一个顶级接口或者父类。这里我们定义一个接口——算法策略

public interface AlgorithmStrategy {
    /**
     * 创造策略
     */
    void creatStrategy();
}

定义2个算法子类,分别实现它
向下取整策略

public class RoundDownStrateg implements AlgorithmStrategy{
    @Override
    public void creatStrategy() {
        System.out.println("执行策略:向下取整");
    }
}

四舍五入策略

public class RoundHalfUpStrategy implements AlgorithmStrategy{
    @Override
    public void creatStrategy() {
        System.out.println("执行策略:四舍五入");
    }
}

激活类

public class AlgorithmStrategyActive {
    /**
     * 算法策略
     */
    private AlgorithmStrategy algorithmStrategy;
    /**
     * 构造方法
     *
     * @param algorithmStrategy 算法策略
     */
    public AlgorithmStrategyActive(AlgorithmStrategy algorithmStrategy) {
        this.algorithmStrategy = algorithmStrategy;
    }
    /**
     * 执行 - 调用的是子类自己的实现
     */
    public void execute(){
        algorithmStrategy.creatStrategy();
    }
}

测试类

public class Test {
    public static void main(String[] args) {
        AlgorithmStrategyActive strategyActive = matchingAlgorithm("roundDown");
        strategyActive.execute();
    }
    private static AlgorithmStrategyActive matchingAlgorithm(String type) {
        AlgorithmStrategyActive strategy = null;
        // 四舍五入
        if ("roundHalfUp".equals(type)){
            // 注册四舍五入策略
            strategy  = new AlgorithmStrategyActive(new RoundHalfUpStrategy());
        }
        // 向下取整
        else if ("roundDown".equals(type)){
            // 注册向下取整策略
            strategy = new AlgorithmStrategyActive(new RoundDownStrateg());
        }
        return strategy;
    }
}

执行结果
图片

结合工厂模式优化

这样我们第一版重构就OK了,但是虽然使用了策略模式,但是我们并没有消除代码中的if-else。为什么没有消除判断呢?因为我们创建对象的时候,需要明确是哪个对象才能进行创建,所以我们可以把创建对象的这个工作交给工厂去处理(工厂模式传送门)。

接下来请出咱们的工厂类

public class AlgorithmStrategyFactory {
    /**
     * 算法策略放入map中
     */
    private static Map<String,AlgorithmStrategy> ALGORITHM_STRATEGY_MAP = new HashMap<String, AlgorithmStrategy>(16);
    /**
     * 类加载的时候就进行初始化
     */
    static {
        ALGORITHM_STRATEGY_MAP.put("roundHalfUp",new RoundHalfUpStrategy());
        ALGORITHM_STRATEGY_MAP.put("roundDown",new RoundDownStrateg());
    }
    /**
     * 得到算法策略
     * 注:这里的null可以创建一个空策略,避免空指针异常,作者很懒,就不实现了,哈哈
     * @param strategyKey 策略key
     * @return {@link AlgorithmStrategy}
     */
    public static AlgorithmStrategy getAlgorithmStrategy(String strategyKey){
        return strategyKey==null?null:ALGORITHM_STRATEGY_MAP.get(strategyKey);
    }
}

测试类

public class Test {
    public static void main(String[] args) {
        AlgorithmStrategyActive strategyActive = matchingAlgorithm("roundDown");
        strategyActive.execute();
    }
    private static AlgorithmStrategyActive matchingAlgorithm(String type) {
        return new AlgorithmStrategyActive(AlgorithmStrategyFactory.getAlgorithmStrategy(type));
    }
}

结果
图片

总结

工作中单单只用到一种设计模式的情况很少,一般都要根据业务需求做出调整,所以一定要多学习。加油吧,撸码人~

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

第七人格

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值