设计模式11_策略模式

来源:互联网 发布:淘宝卖家利润 编辑:程序博客网 时间:2024/04/28 08:17

1、定义


          策略模式作为一种软件设计模式,指对象有某个行为,但是在不同的场景中,该行为有不同的实现算法。比如每个人都要“交个人所得税”,但是“在美国交个人所得税”和“在中国交个人所得税”就有不同的算税方法。

          策略模式:
              * 定义了一族算法(业务规则);
              * 封装了每个算法;
              * 这族的算法可互换代替(interchangeable)。

  摘自维基百科:(https://zh.wikipedia.org/wiki/%E7%AD%96%E7%95%A5%E6%A8%A1%E5%BC%8F)


2、说明

          策略模式属于对象的行为模式。它的目的是定义一系列算法,把它们一个个封装起来, 并且使得它们可相互替换。比如,代码中有很多算法夹在在一个方法中,或者有很多种情况需要处理,但使用的是if…else…进行处理。这样,时间长了代码就会发酵、腐烂,难以维护。比较好的解决方法是将这些算法分离开来,抽象出接口,使用一个context上下文来注入这个接口,使得在需要某一算法的时候,可以直接通过上下文去获取,降低了代码的复杂度,相应代码的可读性也会提高。
        策略模式的适用场景大致有:(1)如果很多相关的类仅仅是行为有异,“策略”则可以提供用行为来配置一个类的方法,即一个系统可按需动态在若干策略中进行选择;(2)需要对客户隐藏复杂的且与算法相关的数据结构;(3)类定义了多种行为,且这些行为在类中以多条件语句的形式出现。


3、角色

          环境角色(Context):持有对Strategy的引用。

          抽象策略角色(Strategy):通常由一个接口或抽象类实现,此角色给出所有的具体策略类所需的接口,并有具体策略类去实现。

          具体策略角色(ConcreteStrategy):包装了相关的算法或行为,需要实现抽象策略类。


4、类图

这里写图片描述


5、示例

/** * 策略接口类 * @author liqqc * */public interface IStrategy {    /*     * 获取价格     */    public double getPrice(double price);}
/** *  * @author liqqc * */public class Context {    private IStrategy iStrategy;    public Context(IStrategy strategy) {        this.iStrategy = strategy;    }    public Double getQuota(Double price) {        return this.iStrategy.getPrice(price);    }}
/** * 一般用户 * @author liqqc * */public class GeneralUser implements IStrategy {    @Override    public double getPrice(double price) {        System.err.println("you are general user");        return price;    }}
/** * 普通会员 * @author liqqc * */public class VipUser implements IStrategy {    @Override    public double getPrice(double price) {        System.err.println("you are vip ,can get disaccount");        return price * 0.9;    }}
/** * 高级会员 * @author liqqc * */public class HighVipUser implements IStrategy {    @Override    public double getPrice(double price) {        System.err.println("you are high vip, can get a high discount");        return price * 0.5;    }}
/** * 测试 * @author liqqc * */public class Main {    public static void main(String[] args) {        final Double price = 1000.0;        //high vip         IStrategy highVipUser = new HighVipUser();        Context context1 = new Context(highVipUser);        Double discount1 = context1.getQuota(price);        System.err.println("you need pay : " + discount1 + "RMB");        System.err.println();        //vip         IStrategy vipUser = new VipUser();        Context context2 = new Context(vipUser);        Double discount2 = context2.getQuota(price);        System.err.println("you need pay : " + discount2 + "RMB");        System.err.println();        //general         IStrategy generalUser = new GeneralUser();        Context context3 = new Context(generalUser);        Double discount3 = context3.getQuota(price);        System.err.println("you need pay : " + discount3 + "RMB");    }}

      运行结果:

you are high vip, can get a high discountyou need pay : 500.0RMByou are vip ,can get disaccountyou need pay : 900.0RMByou are general useryou need pay : 1000.0RMB

6、总结

          优点:(1)策略模式提供了一种管理相关类型算法的办法。其中,策略类的层级结构定义了若干算法或行为。如果能在其中恰当地使用抽象和继承,可以把公共的代码移到父类中,进而避免代码重复。(2)对于使用大量多重条件(if-else)的代码,使用策略模式可以很好地将其减少消除。由于多重条件语句难以维护,其将算法或行为的逻辑混合在一起,全包在一个多重条件语句里面,阅读起来也很费劲,在开发中应该减少多重条件的使用。

          缺点:(1)对于使用者而言,必须知道所有策略类,并按照需求决定使用哪一个策略类。也就意味使用者必须理解策略类(算法)间的异同,以便选择恰当的策略类,策略模式只适用于使用者知道(策略类)算法或行为的情况下使用。对对于一些特别复杂的算法,也不建议使用。(2)策略模式把具体策略实现都封装成为一个一个的类,如果可选的策略很多的话,那么策略类的数数量会很大,可能会难以维护。

          本文只是简单介绍了策略模式,并未对其进行深入探讨,略显粗糙。希望本文对你有所帮助。


2 0
原创粉丝点击