【java设计模式】之 策略(strategy)模式

举报
程序员私房菜 发表于 2019/02/01 10:11:00 2019/02/01
【摘要】   策略模式在实际中使用的还是挺多的,先来看一个场景:某个市场人员接到单儿后的报价策略,保价策略很复杂,但是可以简单做如下归类:新客户小批量报价 新客户大批量报价 老客户小批量报价 老客户大批量报价  具体选用哪个报价策略,这需要根据实际情况来确定,这时候采用策略模式即可解决这个问题。这个问题中,如果我们不采用策略模式会怎样处理呢?很自然的会想到使用if判断,或者switch…case…来解...

  策略模式在实际中使用的还是挺多的,先来看一个场景:某个市场人员接到单儿后的报价策略,保价策略很复杂,但是可以简单做如下归类:


新客户小批量报价 
新客户大批量报价 
老客户小批量报价 
老客户大批量报价


  具体选用哪个报价策略,这需要根据实际情况来确定,这时候采用策略模式即可解决这个问题。这个问题中,如果我们不采用策略模式会怎样处理呢?很自然的会想到使用if判断,或者switch…case…来解决,根据不同的用户确定不同的报价。类似于如下的结构:


public double getPrice(String type, double price) {
    if(type.equals("新客户小批量")) {
        // 处理报价逻辑
        return price;
    } else if(type.equals("新客户大批量")) {
        // 处理报价逻辑
        return price;
    } 
    //......
}


  或者使用switch….case….,但是很明显有个弊端,这个类型特别多,而且每个类型里面还有自己的算法,如果算法比较复杂的话整个条件的控制代码会变得很长,难以维护。为了解决这个问题,我们可以使用策略模式。 

  策略模式:即对应于解决某一个问题的一个算法族,允许用户从该算法族中人选个一个算法解决某一问题,同时可以方便的更换算法或者增加新的算法,并且由客户端决定调用哪个算法,可以如下的示意图: 

 

image.png


  首先有个策略的接口,然后不同的四个不同的策略分别实现这个接口中的方法,在这里是报价的方法,然后定义一个上下文类,用来操作具体的具体的策略,客户端只需要与这个上下文打交道即可,即只要将策略传给上下文类,就可以执行相应的策略,后期如果需要修改或者添加,只需要修改具体的策略实现类或者新添加一个实现类即可,便于维护。下面来看下程序的实现。


//策略接口
public interface Strategy {
    public double getPrice(double standardPrice);
}


四个不同的策略实现类:


// 新客户小批量
public class NewCustomerFewStrategy implements Strategy {
    @Override
    public double getPrice(double standardPrice) {
        System.out.println("新客户小批量,不打折");
        return standardPrice;
    }
}
// 新客户大批量
public class NewCustomerManyStrategy implements Strategy {
    @Override
    public double getPrice(double standardPrice) {
        System.out.println("新客户大批量,打九折");
        return standardPrice * 0.9;
    }
}
// 老客户小批量
public class OldCustomerFewStrategy implements Strategy {
    @Override
    public double getPrice(double standardPrice) {
        System.out.println("老客户小批量,打八折");
        return standardPrice * 0.8;
    }
}
// 老客户大批量
public class OldCustomerManyStrategy implements Strategy {
    @Override
    public double getPrice(double standardPrice) {
        System.out.println("老客户大批量,打八折");
        return standardPrice * 0.7;
    }
}


然后就是上下文类了:


/**
 * @Description 负责和具体的策略交互,具体的算法和直接的客户端分离。
 * @author Ni Shengwu
 *
 */
public class Context {
    private Strategy strategy;
    // 通过构造方法注入具体的策略,如果用Spring,就可以直接使用@Resource来注入了
    public Context(Strategy strategy) {
        super();
        this.strategy = strategy;
    }
    public void getPrice(double standardPrice) {
        System.out.println("报价为:" + strategy.getPrice(standardPrice));
    }
}


测试一下:


public class Client {
    public static void main(String[] args) {
        Strategy s1 = new OldCustomerManyStrategy();
        Context ctx = new Context(s1); //通过构造方法注入策略
        ctx.getPrice(1000);
    }
}


输出结果为:


老客户大批量,打八折 
报价为:700.0


在实际中,策略模式在spring中也有用到,通过注解@Resource就是使用该模式,注入哪个就使用哪个。 



【版权声明】本文为华为云社区用户原创内容,转载时必须标注文章的来源(华为云社区)、文章链接、文章作者等基本信息, 否则作者和本社区有权追究责任。如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。