Java设计模式——策略模式

实习做的项目,有那么几个功能举要疯狂的使用if-else来进行判断,之前老哥用了工厂模式进行解决。翻看阿里的Java手册发现推荐使用…卫语句,策略模式或状态模式。在这里插入图片描述
卫语句和if-else相比区别不大,无非就是可读性更强了一些,但是维护难度一点没降低,可扩展性一点没提高。一旦需求更改,需要修改所有使用更改需求的if-else代码块。不变还好一变想想都闹心。所以还是看看这个策略模式。


策略模式

0.简介

个人理解,从代码角度来看,策略模式就是OOP封装的体现,他定义一系列的算法,用不同的类把它们一个个封装起来, 共同实现一个接口。
其中需要调用这个算法的地方称之为——环境(Context)
共同实现的接口称之为——抽象策略(Strategy)角色
每一个具体的实现类称之为——具体策略(ConcreteStrategy)角色

1.结构

我们按照这个可以简单的写个框架。
环境

public class Context {
    // 持有一个具体策略的对象
    private Strategy strategy;

    public Context(Strategy strategy) {
        this.strategy = strategy;
    }

    // 策略方法
    public void contextMethod() {
        strategy.strategyMethod();
    }

}

抽象策略角色

/**
 * @Description:抽象策略
 * @Author: scz
 */
public interface Strategy {
    /**
     * @Description:规定的策略方法
     * @Return: void
     * @Author: scz
     */
    void strategyMethod();

}

具体策略

/**
 * @Description:具体策略方法
 * @Author: scz
 */
public class ConcreteStrategyA implements Strategy {
    @Override
    public void strategyMethod() {
        //TODO 具体实现
    }
}

2.实例

下班回家,可以坐公交也可以,骑车也可以,有两种策略。
回家的人的名字作为参数进行传递。
首先创建策略接口

package com.inter;
public interface GoHomementStrategy {
    /**
     * @Description:回家抽象策略接口
     * @Date: 17:17 2019-08-06
     * @Param: [name]
     * @Return: void
     * @Author: scz
     */
    public void gohome(String name);
}

具体策略实现
坐公交

package com.impl;

import com.inter.GoHomementStrategy;

public class BusGoHomementStrategy implements GoHomementStrategy {
    private Integer money;
    private String time;

    public BusGoHomementStrategy(Integer money, String time) {
        this.money = money;
        this.time = time;
    }
    /**
     * @Description: 坐公车回家具体策略
     * @Date: 17:06 2019-08-06
     * @Param: [name] 回家人名字
     * @Return: void
     * @Author: scz
     */
    @Override
    public void gohome(String name) {
        System.out.println(name+"坐公交回家啦~");
    }
}

骑车

package com.impl;

import com.inter.GoHomementStrategy;

public class BicycleGoHomementStrategy implements GoHomementStrategy {
    private Integer money;
    private String time;

    public BicycleGoHomementStrategy(Integer money, String time) {
        this.money = money;
        this.time = time;
    }
    /*
     * @Description:骑车回家人具体策略
     * @Date: 17:06 2019-08-06
     * @Param: [name] 回家人名字
     * @Return: void
     * @Author: scz
     */
    @Override
    public void gohome(String name) {
        System.out.println(name+"骑车回家啦~");
    }
}

工作人类,让他自己选怎么回家

package com.text;

import com.inter.GoHomementStrategy;

public class WorkerContext {
    private GoHomementStrategy goHomementStrategy;

    /**
     * 决策使用什么方法回家
     * @param name
     */
    public void goHome(String name){
        goHomementStrategy.gohome(name);
    }

    public WorkerContext() {
    }

    public WorkerContext(GoHomementStrategy goHomementStrategy) {
        this.goHomementStrategy = goHomementStrategy;
    }

    public GoHomementStrategy getGoHomementStrategy(){
        return goHomementStrategy;
    }

    public void setGoHomementStrategy(GoHomementStrategy goHomementStrategy) {
        this.goHomementStrategy = goHomementStrategy;
    }
}

测试下

package com.test;

import com.impl.BicycleGoHomementStrategy;
import com.impl.BusGoHomementStrategy;
import com.text.WorkerContext;

public class GoHomementClient {
    public static void main(String[] args) {
        // 创建用户
        // 创建公交回家策略
        WorkerContext workerContext = new WorkerContext();
        BusGoHomementStrategy busGoHomementStrategy = new BusGoHomementStrategy (1, "2");
        workerContext.setGoHomementStrategy(busGoHomementStrategy);
        // 创建骑车回家策略
        WorkerContext workerContextBy = new WorkerContext();
        BicycleGoHomementStrategy bicycleGoHomementStrategy = new BicycleGoHomementStrategy(1,"2");
        workerContextBy.setGoHomementStrategy(bicycleGoHomementStrategy);
        // 公交回家啦~
       workerContext.goHome("scz");
       //骑车回家啦~
        workerContextBy.goHome("zcs");
    }

}

运行结果:
在这里插入图片描述

3.总结

  1. 完美符合 OCP 原则,可以看到 Context 对象对修改是关闭的,添加新的策略,不需要修改
    Context,代码后期维护性以及可扩展性非常高(优点);
  2. 客户端或用户必须知道所有的策略类,并自行决定使用哪一个策略类(缺点);
    每增加一个策略,设计中类的数目也会相应增加,这是为了要获得程序的可扩展性及弹性所付出的代价(缺点)。
  3. 如果你的代码不是一次性的,后期可能会不断加入不同的策略,那么策略模式的设计是绝对值得的。

参考博客:https://blog.csdn.net/championhengyi/article/details/86649264

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值