牛骨文教育服务平台(让学习变的简单)

策略模式,顾名思义,就是在一个问题有多种解决方法的时候应用哪种方法,哪种策略来完成而设计的一种模式,以达到高解耦,灵活性高,代码更加清晰明了。策略模式又是一种面向对象的设计模式,说白了,所有的这些模式的出现都是为了使程序或者代码结构更加清晰,易于理解,降低耦合性,提高灵活性以使代码更加容易扩展等等。

定义:策略模式定义了一系列算法,并将每个算法封装起来,而且使得它们可以相互替换,策略模式让算法和使用它的客户端而独立变化。

策略模式的使用场景:

  1. 针对一个问题有多种解决方法的时候,用来选择具体的哪种方法。

  2. 将多种同类型的操作独立封装起来, 保证多种同类型的操作安全性。当我们的程序有多种同类型的方法时我们不应该因为添加了新类型的方法而要改变原来的方法,不然就违背了OCP(开闭)原则和单一职责原则。

  3. 摆脱臃肿。当出现同一个类有多个子类时选择哪个子类而不需要if-else或者switch-else。

策略模式的优点:

  1. 结构清晰明了,使用简单直观。使用时根据需要选择不同的策略;

  2. 耦合度较低,灵活性高,易扩展;

  3. 操作(策略)封装比较彻底,数据更加安全。

策略模式的缺点:

  • 随着策略数量增加的增加,需要的策略子类越来越多,程序体积变大。

策略模式的实现:

路线情况:

/**
 * 乘车的路线情况
 * @author lt
 *
 */
public class Route {

    public String type; // 路的类型,如:水路
    public int money; // 消耗的路费
    public String time; // 花费的时间

    @Override
    public String toString() {
        return "Route [type=" + type + ", money=" + money + ", time=" + time
                + "]";
    }
}

抽象乘车策略类:

/**
 * 乘车策略
 * @author lt
 *
 */
public abstract class RideStrategy {

    /**
     * 计算乘车价格
     * @return
     */
    public abstract Route CalcuRidePrice();
}

走水路:

/**
 * 水路,这是一种策略
 * @author Administrator
 *
 */
public class Waterway extends RideStrategy {

    @Override
    public Route CalcuRidePrice() { 
        Route route = new Route();
        route.type = "水路";
        route.money = 100;
        route.time = "2个小时";
        return route;
    }
}

走陆路:

/**
 * 陆路,这是一种策略
 * @author lt
 *
 */
public class Randway extends RideStrategy {

    @Override
    public Route CalcuRidePrice() {
        Route route = new Route();
        route.type = "陆路";
        route.money = 180;
        route.time = "1个半小时";
        return route;
    }
}

走空路:

/**
 * 空路,乘飞机,这是一种策略
 * @author lt
 *
 */
public class Airway extends RideStrategy {

    @Override
    public Route CalcuRidePrice() {
        Route route = new Route();
        route.type = "空路";
        route.money = 400;
        route.time = "20分钟";
        return route;
    }
}

乘车:

/**
 * 乘车
 * @author lt
 *
 */
public class Ride {

    private RideStrategy rideStrategy;

    /**
     * 获取路线情况
     * @return
     */
    public Route getRoute(){
        return rideStrategy.CalcuRidePrice();
    }

    public RideStrategy getRideStrategy() {
        return rideStrategy;
    }

    public void setRideStrategy(RideStrategy rideStrategy) {
        this.rideStrategy = rideStrategy;
    }
}

测试使用这三种策略:

public class Test {

    public static void main(String[] args) {
        Ride ride = new Ride();
        // 1. 走水路
        ride.setRideStrategy(new Waterway());
        System.out.println(ride.getRoute());

        // 2. 走陆路
        ride.setRideStrategy(new Randway());
        System.out.println(ride.getRoute());

        // 3. 走空路
        ride.setRideStrategy(new Airway());
        System.out.println(ride.getRoute());
    }
}

结果:
这里写图片描述

可以看到,上面我们测试的方法里面这三种策略只是换了一个实现而已,源码什么了都没修改,仅仅改变了策略,这就实现了这三种策略的使用。而且以后如果各路线的情况改变了,比如水路涨价了,那么我们只需要修改水路那种策略,即:只要修改Waterway.java这个类而不用修改其他策略(陆路和空路),保证了其他策略(陆路和空路)的安全,并且以后如果有其他种类的路线(除了海陆空),那么相应的只需要增加一个策略类而已,极易扩展和使用。

总结:
策略模式的引入使得我们的程序结构更加清晰明了,耦合性降低,灵活性提升,在面对实际的一个操作有多种算法或者策略实现的情况下应多使用这种模式。