关于策略模式的理解和简单案例(结合单例工厂的优雅实现)

策略模式

算法家族里面有很多的算法,封装起来,让彼此之间可以相互交替使用,使用某一个算法的用户不会受到影响,为了减少各种算法类和使用算法类之间的耦合。策略模式的应用场景:一个系统中有很多的类,区别只是行为不同。

我们接下来以一些简单案例来更好的理解

首先创建一个接口

package promotion;

/**
 * 优惠活动
 * @author lp
 */
public class PromotionAction {
     //单例模式
    private PromotionStrategy promotionStrategy;
    public PromotionAction(PromotionStrategy promotionStrategy){
        this.promotionStrategy=promotionStrategy;
    }

    /**
     * 执行优惠的方法
     */
    public void execute(){
        promotionStrategy.doPromotion();
    }
}

然后创建执行优惠方法的类

package promotion;

/**
 * 优惠活动
 * @author lp
 */
public class PromotionAction {
     //单例模式
    private PromotionStrategy promotionStrategy;
    public PromotionAction(PromotionStrategy promotionStrategy){
        this.promotionStrategy=promotionStrategy;
    }

    /**
     * 执行优惠的方法
     */
    public void execute(){
        promotionStrategy.doPromotion();
    }
}

分别创建不同的类实现接口模拟不同的优惠

package promotion;

/**
 * 返现策略
 * @author lp
 */
public class CashBackStrategy implements PromotionStrategy {
   
    @Override
    public void doPromotion() {
        System.out.println("返回现金到支付宝");

    }
}

 

package promotion;

/**
 * 优惠券策略
 * @author lp
 */
public class CouponStrategy implements PromotionStrategy{
    @Override
    public void doPromotion() {
        System.out.println("领取优惠券打折");
    }
}

 

package promotion;

/**
 * 没有任何优惠
 */
public class EmptyStrategy implements PromotionStrategy {
    @Override
    public void doPromotion() {
        System.out.println("没有优惠");

    }
}

 

package promotion;

/**
 * 团购优惠
 * @author lp
 */
public class GroupBuyStragety implements PromotionStrategy {
    @Override
    public void doPromotion() {
        System.out.println("团购优惠");

    }
}

 

这是简单的实现,下面进行测试这里大家都会

  /**
     *
     * 第一次测试
     */
//    public static void main(String[] args) {
//        //模拟双十一打折
//        PromotionAction action1111=new PromotionAction(new GroupBuyStragety());
//        //模拟618打折
//        PromotionAction action618=new PromotionAction(new CouponStrategy());
//        action1111.execute();
//        action618.execute();
//        //如果后期增加许多功能,作为程序编写人员,业务增加比较繁琐
//        //如何进行优化??
//
//
//    }

然后思考如何进行优化

可以这样来测试:

这里面的string promotionKey就是相对应的优惠的名称,根据这个名称实例化不同的优惠策略,这里用了多个else if 方便了后期增加需求,但是这样写代码还是显得十分臃肿,不够优雅。

   /**
     *
     * 简单优化后测试
     */
//    public static void main(String[] args) {
//        //定义一个对象
//        PromotionAction promotionAction=null;
//        //定义优惠的key,这里是优惠券
//        String promotionKey="COUPON";
//        //如果匹配的是优惠券,那就实例化优惠券的策略
//        if(StringUtils.equals(promotionKey,"COUPON")){
//            promotionAction=new PromotionAction(new CouponStrategy());
//        //如果是返现,实例化就是返现策略
//        }else if(StringUtils.equals(promotionKey,"CASHBACK")){
//            promotionAction=new PromotionAction(new CashBackStrategy());
//        }//。。。。不管后面有多少都是else if
//        promotionAction.execute();
//
//    }

 

最后一种,使用工厂单例的策略模式,创建一个工厂类

package promotion;

import java.util.HashMap;
import java.util.Map;

/**
 * 促销策略工厂
 * @author lp
 */
public class PromotionStrategyFactory {
    private static Map<String,PromotionStrategy> PROMOTION_STRATEGY_MAP=new HashMap<>();

    static{
        //优惠券
        PROMOTION_STRATEGY_MAP.put(PromotionKey.COUPON,new CouponStrategy());
        //返现
        PROMOTION_STRATEGY_MAP.put(PromotionKey.CASHBACK,new CashBackStrategy());
        //团购
        PROMOTION_STRATEGY_MAP.put(PromotionKey.GROUPBUY,new GroupBuyStragety());
    }
    //实例化一个没有打折的情况
    private static final PromotionStrategy NON_PROMOTION=new EmptyStrategy();
    //构造
    private  PromotionStrategyFactory(){}
    //根据对应的key值,实例化不同的策略
    public static PromotionStrategy getPromotionStrategy(String promotionKey){
        PromotionStrategy promotionStrategy=PROMOTION_STRATEGY_MAP.get(promotionKey);
        return promotionStrategy==null?NON_PROMOTION:promotionStrategy;
    }
    //定义接口常量,可以用枚举比较推荐
    private interface PromotionKey{
        String COUPON="COUPON";
        String CASHBACK="CASHBACK";
        String GROUPBUY="GROUPBUY";
    }
}

然后再看测试类如何写

public static void main(String[] args) {
    //策略模式:单例+工厂
   这里的promotionKey,根据你定义的api常量里面选取就可以了,实现分离开来
实现了解耦,方便后期的维护增加功能等
    String promotionKey="COUPON";
    PromotionAction promotionAction=new PromotionAction(PromotionStrategyFactory.getPromotionStrategy(promotionKey));
    promotionAction.execute();
}

 

 

 

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 5
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值