设计模式之策略模式

来源:互联网 发布:知乎可以邮箱注册吗 编辑:程序博客网 时间:2024/06/06 00:55

概念:
       策略模式属于对象的行为模式。其用意是针对一组算法,将每一个算法封装到具有共同接口的独立的类中,从而使得它们可以相互替换。策略模式使得算法可以在不影响到客户端的情况下发生变化。


类图:


       ●  环境(Context)角色:持有一个Strategy的引用。

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

  ●  具体策略(ConcreteStrategy)角色:包装了相关的算法或行为。


使用场景:

     假设某个商店对所有的高级会员提供每本20%的促销折扣;对中级会员提供每本10%的促销折扣;对初级会员没有折扣;计算同一个价格不同策略下的输出
/** *  @Author: fc *  @Date: 19:30 2017/10/25 */interface MemberStrategy {    /**     * 计算图书的价格     * @param booksPrice    图书的原价     * @return    计算出打折后的价格     */    fun calcPrice(booksPrice: Double): Double}
class PrimaryMemberStrategy:MemberStrategy {    override fun calcPrice(booksPrice: Double): Double {        println("对于初级会员的没有折扣")        return  booksPrice    }}
class AdvancedMemberStrategy:MemberStrategy {    override fun calcPrice(booksPrice: Double): Double {        println("对于高级会员的折扣为20%")        return booksPrice * 0.8    }}
class Price(strategy: MemberStrategy) {    //持有一个具体的策略对象    var mStrategy: MemberStrategy? = strategy    fun setMemberStrategy(strategy: MemberStrategy){        mStrategy = strategy    }    fun calculate(booksPrice: Double): Double {        return mStrategy?.calcPrice(booksPrice)!!    }}
测试类:
fun main(args: Array<String>) {    val strategy = AdvancedMemberStrategy()    val price = Price(strategy)    println("图书的最终价格为:"+price.calculate(100.00))    val primaryStrategy = PrimaryMemberStrategy()    price.setMemberStrategy(primaryStrategy)    println("图书的最终价格为:"+price.calculate(100.00))}
运行结果:
     对于高级会员的折扣为20%
     图书的最终价格为:80.0
     对于初级会员的没有折扣
     图书的最终价格为:100.0


优点:
    1.策略类之间可以自由切换,由于策略类实现自同一个抽象,所以他们之间可以自由切换。
    2.易于扩展,增加一个新的策略对策略模式来说非常容易,基本上可以在不改变原有代码的基础上进行扩展。
    3.易于维护,使用策略模式可以避免使用多重条件(if-else)语句。
 
缺点:
     1.客户端必须知道所有的策略类,并自行决定使用哪一个策略类。
     2.类的个数会比较多,因为策略模式把每个具体的策略实现都单独封装成为类
  
  
 
  策略模式是一种简单常用的模式,我们在进行开发的时候,会经常有意无意地使用它,一般来说,策略模式不会单独使用,跟模版方法模式、工厂模式等混合使用的情况比较多。