简介
策略模式(Strategy Pattern)又叫做政策模式(Policy Pattern),它是将定义的算法家族、分别封装起来,让它们之间可以相互替换,从而让算法的变化不会影响到使用算法的用户。属于行为型模式。
策略模式使用的就是面向对象的继承和多态机制,从而实现同一行为在不同场景下具备不同实现。
策略模式的应用场景
策略模式可以解决在有多种算法相似的情况下,使用if...else或switch...case所带来的复杂性和臃肿性。在日常业务中,策略模式适用于以下场景:
1、针对同一类型问题,有多种处理方式,每一种都能独立解决问题;
2、算法需要自由切换的场景;
3、需要屏蔽算法规则的场景。
策略模式的UML类图:
从UML类图中,我们可以看到,策略模式主要包含三种角色:
上下文角色(Context):用来操作策略的上下文环境,屏蔽高层模块(客户端)对策略,算法的直接访问,封装可能存在的变化;
抽象策略角色(Strategy):规定策略或算法的行为;
具体策略角色(ConcreteStrategy)具体的策略或算法实现。
策略模式在框架源码中的体现
1、JDK中常用的比较器Comparator接口
public interface Comparator<T> {
int compare(T o1, T o2);
...
}
Comparator抽象下面有许多的实现类,我们通常会把Comparator作为参数传入作为排序策略。
-
Arrays类的
paralleSort
方法public class Arrays { public static <T> void parallelSort(T[] a, int fromIndex, int toIndex, Comparator<? super T> cmp) { ... } ... }
-
TreeMap的构造方法
public class TreeMap<K,V> extends AbstractMap<K,V> implements NavigableMap<K,V>, Cloneable, java.io.Serializable { public TreeMap(Comparator<? super K> comparator) { this.comparator = comparator; } ... }
2、Comparator在Spring源码中的应用
- Resource类
-
Spring中bean实例化策略 ---
InstantiationStrategy
实例化策略接口类接口`InstantiationStrategy`是实例化策略接口类,它定义了三个实例化接口,然后`SimpleInstantiationStrategy`实现了该策略,它主要做一些简单的根据构造函数实例号bean的工作,然后 `CglibSubclassingInstantiationStrategy`又继承了`SimpleInstantiationStrategy`新增了方法注入方式根据cglib生成代理类实例化方法。 在`AbstractAutowireCapableBeanFactory`中管理了该策略的一个对象,默认是`CglibSubclassingInstantiationStrategy`策略,运行时候可以通过`setInstantiationStrategy`改变实例化策略。
从图中来看,说明在实际应用中多种策略之间还可以继承使用。
策略模式的优缺点:
优点:
1、策略模式符合开闭原则
2、避免使用多种条件转移语句,如if...else..语句、switch语句
3、使用策略模式可以提高算法的保密性和安全性。
缺点:
1、客户端必须知道所有的策略,并且自行决定使用哪一种策略类
2、代码中会产生非常多策略类,增加维护难度。