23种设计模式(12):策略模式

定义:定义一组算法,将每一个算法都封装起来,而且使他们之间能够互换。 html

类型:行为类模式 算法

类图: 编程

23种设计模式(12):策略模式 - 第1张  | 快课网

策略模式是对算法的封装,把一系列的算法分别封装到对应的类中,而且这些类实现相同的接口,相互之间能够替换。在前面说过的行为类模式中,有一种模式也是关注对算法的封装——模版方法模式,对照类图能够看到,策略模式与模版方法模式的区别仅仅是多了一个单独的封装类Context,它与模版方法模式的区别在于:在模版方法模式中,调用算法的主体在抽象的父类中,而在策略模式中,调用算法的主体则是封装到了封装类Context中,抽象策略Strategy通常是一个接口,目的只是为了定义规范,里面通常不包含逻辑。其实,这只是通用实现,而在实际编程中,由于各个具体策略实现类之间不免存在一些相同的逻辑,为了不重复的代码,咱们经常使用抽象类来担任Strategy的角色,在里面封装公共的代码,所以,在不少应用的场景中,在策略模式中通常会看到模版方法模式的影子。 设计模式

 

策略模式的结构 数组

  • 封装类:也叫上下文,对策略进行二次封装,目的是避免高层模块对策略的直接调用。
  • 抽象策略:一般状况下为一个接口,当各个实现类中存在着重复的逻辑时,则使用抽象类来封装这部分公共的代码,此时,策略模式看上去更像是模版方法模式。
  • 具体策略:具体策略角色一般由一组封装了算法的类来担任,这些类之间能够根据须要自由替换。

策略模式代码实现 this

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
interface IStrategy {
     public void doSomething ( ) ;
}
class ConcreteStrategy1 implements IStrategy {
     public void doSomething ( ) {
         System . out . println ( "具体策略1" ) ;
     }
}
class ConcreteStrategy2 implements IStrategy {
     public void doSomething ( ) {
         System . out . println ( "具体策略2" ) ;
     }
}
class Context {
     private IStrategy strategy ;
 
     public Context ( IStrategy strategy ) {
         this . strategy = strategy ;
     }
 
     public void execute ( ) {
         strategy . doSomething ( ) ;
     }
}
 
public class Client {
     public static void main ( String [ ] args ) {
         Context context ;
         System . out . println ( "-----执行策略1-----" ) ;
         context = new Context ( new ConcreteStrategy1 ( ) ) ;
         context . execute ( ) ;
 
         System . out . println ( "-----执行策略2-----" ) ;
         context = new Context ( new ConcreteStrategy2 ( ) ) ;
         context . execute ( ) ;
     }
}

 

策略模式的优缺点 spa

策略模式的主要优势有: 设计

  • 策略类之间能够自由切换,因为策略类实现自同一个抽象,因此他们之间能够自由切换。
  • 易于扩展,增长一个新的策略对策略模式来讲很是容易,基本上能够在不改变原有代码的基础上进行扩展。
  • 避免使用多重条件,若是不使用策略模式,对于全部的算法,必须使用条件语句进行链接,经过条件判断来决定使用哪种算法,在上一篇文章中咱们已经提到,使用多重条件判断是很是不容易维护的。

策略模式的缺点主要有两个: code

  • 维护各个策略类会给开发带来额外开销,可能你们在这方面都有经验:通常来讲,策略类的数量超过5个,就比较使人头疼了。
  • 必须对客户端(调用者)暴露全部的策略类,由于使用哪一种策略是由客户端来决定的,所以,客户端应该知道有什么策略,而且了解各类策略之间的区别,不然,后果很严重。例如,有一个排序算法的策略模式,提供了快速排序、冒泡排序、选择排序这三种算法,客户端在使用这些算法以前,是否是先要明白这三种算法的适用状况?再好比,客户端要使用一个容器,有链表实现的,也有数组实现的,客户端是否是也要明白链表和数组有什么区别?就这一点来讲是有悖于迪米特法则的。

 

适用场景 htm

作面向对象设计的,对策略模式必定很熟悉,由于它实质上就是面向对象中的继承和多态,在看完策略模式的通用代码后,我想,即便以前历来没有据说过策略模式,在开发过程当中也必定使用过它吧?至少在在如下两种状况下,你们能够考虑使用策略模式,

  • 几个类的主要逻辑相同,只在部分逻辑的算法和行为上稍有区别的状况。
  • 有几种类似的行为,或者说算法,客户端须要动态地决定使用哪种,那么可使用策略模式,将这些算法封装起来供客户端调用。

策略模式是一种简单经常使用的模式,咱们在进行开发的时候,会常常有意无心地使用它,通常来讲,策略模式不会单独使用,跟模版方法模式工厂模式等混合使用的状况比较多。

相关文章
相关标签/搜索