設計模式(22) 策略模式

在策略模式中,一個類的行爲或算法能夠在運行時動態更改。算法

GOF對策略模式的描述爲:
Define a family of algorithms, encapsulate each one, and make them interchangeable. Strategy lets the algorithm vary independently from clients.
— Design Patterns : Elements of Reusable Object-Oriented Softwarethis

UML類圖以下:
3d

策略模式包含三個角色:code

  • Context上下文角色,起承上啓下封裝做用,屏蔽高層模塊對策略、算法的直接訪問,封裝可能存在的變化。
  • Strategy抽象策略角色,策略、算法家族的抽象,一般爲接口,定義每一個策略或算法必須具備的方法和屬性。
  • ConcreteStrategy具體策略角色,實現抽象策略中的操做,該類含有具體的算法。

代碼示例:
以電商會員折扣爲例,不一樣級別的會員享受的折扣是不一樣的,這種差別能夠用策略模式來封裝。對象

public interface Strategy
{
    double CalcPrice(double originalPrice);
}

public class PrimaryStrategy : Strategy
{
    public double CalcPrice(double originalPrice)
    {
        return originalPrice;
    }
}

public class IntermediateStrategy : Strategy
{
    public double CalcPrice(double originalPrice)
    {
        return originalPrice * 0.9;
    }
}
public class AdvancedStrategy : Strategy
{
    public double CalcPrice(double originalPrice)
    {
        return originalPrice * 0.8;
    }
}

public class PriceContext
{
    public Strategy Strategy { get; set; }

    public double GetPrice(double originalPrice)
    {
        return this.Strategy.CalcPrice(originalPrice);
    }
}

調用端:blog

public class Test
{
    public static void Entry()
    {
        Strategy strategy = new PrimaryStrategy();
        PriceContext price = new PriceContext();
        price.Strategy = strategy;

        Console.WriteLine(price.GetPrice(100)); //100

        strategy = new IntermediateStrategy();
        price.Strategy = strategy;
        Console.WriteLine(price.GetPrice(100)); //90

        strategy = new AdvancedStrategy();
        price.Strategy = strategy;
        Console.WriteLine(price.GetPrice(100)); //80
    }
}

示例中有若干具體的策略類,以及一個context對象,context對象會隨着策略對象的改變而變動其執行算法。接口

策略模式的優勢get

  • 算法能夠自由切換,只要實現抽象策略,它就成爲策略家族的一個成員,經過封裝角色對其進行封裝,保證對外提供「可自由切換」的策略。
  • 避免使用多重條件判斷,多重條件語句不易維護,並且出錯的機率較大。使用策略模式後,能夠由其餘模塊決定採用何種策略,策略家族對外提供的訪問接口就是封裝類,簡化了操做,同時避免了條件語句判斷。
  • 擴展性良好,在現有的系統中增長一個策略很是容易,只要實現接口就能夠了。

策略模式的缺點it

  • 策略類數量增多,每個策略都是一個類,複用的可能性很小,類數量增多。
  • 全部的策略類都須要對外暴露,上層模塊必須知道有哪些策略,並瞭解這些策略之間的區別,而後才能決定使用哪個策略,這與迪米特法則是相違背的。

策略模式的適用場景電商

  • 多個類只有在算法或行爲上稍有不一樣的場景。
  • 算法須要自由切換的場景。
相關文章
相關標籤/搜索