1. 程式人生 > >用心理解設計模式——策略模式 (Strategy Pattern)

用心理解設計模式——策略模式 (Strategy Pattern)

前置文章: 用心理解設計模式——設計模式的原則 

設計模式相關程式碼已統一放至 我的 Github

 

一、定義

  行為型模式之一。 

  Define a family of algorithms, encapsulate each one, and make them interchangeable.

  (定義一組演算法,將每個演算法都封裝起來,並使它們之間可以互換。)

二、結構解析

  策略模式的一般結構有三種角色: 抽象策略、具體策略、環境/上下文。

  抽象策略,為將要封裝的演算法提供一個公共介面方法。

  具體策略,實現抽象策略定義的介面方法。

  環境/上下文,持有具體策略,並可靈活切換;對外,為高層模組提供一個介面方法。

三、評價

  策略模式,作為行為型模式之一,它將 “策略” 這個抽象概念抽象為類,並定義了為滿足不同需求對 “策略” 進行切換的行為過程。讓策略演算法得以從客戶邏輯中剝離出來,減輕客戶類負擔,降低程式複雜度。

  策略模式符合開閉原則(避免了條件分支語句的出現,通過派生新類使策略易擴充套件)。

  策略模式中的 “環境/上下文類” 是策略模式的重點。該類對具體策略進行了封裝和額外的處理(用策略演算法實現為高層模組提供的對外介面),避免了客戶類對策略類的直接呼叫,符合迪米特法則

(讓客戶只用關心自己要做的,不用關心怎麼組織演算法達成目標)。

四、實現

using UnityEngine;

namespace Strategy
{
    //抽象策略
    public abstract class Strategy
    {
        public abstract void AlgorithmInterface();
    }

    //具體策略A,實現A演算法
    public class ConcretesStrategyA : Strategy
    {
        public override void AlgorithmInterface()
        {
            Debug.Log("演算法A");
        }
    }

    //具體策略A,實現B演算法
    public class ConcretesStrategyB : Strategy
    {
        public override void AlgorithmInterface()
        {
            Debug.Log("演算法B");
        }
    }

    //環境/上下文,持有具體策略,並可靈活切換;對外,為高層模組提供一個介面方法,方法中對策略進行封裝或額外的組織,避免高層模組對策略的直接呼叫。
    public class Context
    {
        Strategy strategy;
        public Context(Strategy strategy)
        {
            this.strategy = strategy;
        }

        public void DoSth()
        {
            //額外的預先操作
            this.Before();
            //最終呼叫真實主題的業務方法
            this.strategy.AlgorithmInterface();
            //額外的後續操作
            this.After();
        }

        private void Before() { }
        private void After() { }
    }

    //客戶
    public class Client
    {
        static public void Main()
        {
            Context contextA = new Context(new ConcretesStrategyA());
            Context contextB = new Context(new ConcretesStrategyB());

            contextA.DoSth();
            contextB.DoSth();
        }
    }
}