天天看點

設計模式——政策設計模式

1 什麼是政策模式?

    政策模式講的是,如果有一組算法将來它們可能因為需求的原因而發生變更,那麼可以将每一個算法都封裝起來,使得他們可以互互相換。這樣可以在保證系統中原有代碼幾乎不變更的情況下,隻需增加算法的一種實作,即可實作功能的變更。

2 政策模式有什麼好處?

     政策模式的好處在于可以保證原有代碼幾乎不變的情況下,實作功能上的擴充,具體展現在可以動态的改變對象的行為. 政策模式遵循了ocp(“開-閉”)的設計原則,一個良好的軟體對内是封閉的,對外是易于開放的。

3 設計原則

     設計原則是把一個類中經常改變或者将來可能改變的部分提取出來,作為一個接口,然後在類中包含這個對象的執行個體,這樣類的執行個體在運作時就可以随意調用實作了這個接口的類的行為。

4 政策模式的結構

政策模式中有三個對象:

(1) 環境對象:該類中實作了對抽象政策中定義的接口或者抽象類的引用。

(2) 抽象政策對象:它可由接口或抽象類來實作。

(3) 具體政策對象:它封裝了實作同不功能的不同算法。

      利用政策模式建構應用程式,可以根據使用者配置等内容,選擇不同有算法來實作應用程式的功能。具體的選擇有環境對象來完成。采用這種方式可以避免由于使用條件語句而帶來的代碼混亂,提高應用程式的靈活性與條理性。

5 應用場景舉例(這個是借鑒别人的)

    劉備要到江東娶老婆了,走之前諸葛亮給趙雲(伴郎)三個錦囊妙計,說是按天機拆開能解決棘手問題,嘿,還别說,真解決了大問題,搞到最後是周瑜陪了夫人又折兵,那咱們先看看這個場景是什麼樣子的。

先說說這個場景中的要素:三個妙計,一個錦囊,一個趙雲,妙計是亮哥給的,妙計放在錦囊裡,俗稱就是錦囊妙計嘛,那趙雲就是一個幹活的人,從錦囊取出妙計,執行,然後獲勝。用java程式怎麼表現這些呢?

那我們先來看看圖?

設計模式——政策設計模式

三個妙計是同一類型的東西,那咱就寫個接口:

Java代碼  

  1. package com.yangguangfu.strategy;  
  2. public interface IStrategy {  
  3.     //每個錦囊妙計都是一個可執行的算法。  
  4.     public void operate();  
  5. }  

然後再寫三個實作類,有三個妙計嘛:

妙計一:初到吳國:

Java代碼  

  1. package com.yangguangfu.strategy;  
  2. public class BackDoor implements IStrategy {  
  3.     @Override  
  4.     public void operate() {  
  5.         System.out.println("找喬國老幫忙,讓吳國太給孫權施加壓力,使孫權不能殺劉備...");  
  6.     }  
  7. }  

妙計二:求吳國太開個綠燈,放行:

Java代碼  

  1. package com.yangguangfu.strategy;  
  2. public class GivenGreenLight implements IStrategy {  
  3.     @Override  
  4.     public void operate() {  
  5.         System.out.println("求吳國太開個綠燈,放行!");  
  6.     }  
  7. }  

 妙計三:孫夫人斷後,擋住追兵:

Java代碼  

  1. package com.yangguangfu.strategy;  
  2. public class BlackEnemy implements IStrategy {  
  3.     @Override  
  4.     public void operate() {  
  5.         System.out.println("孫夫人斷後,擋住追兵...");  
  6.     }  
  7. }  

好了,大家看看,三個妙計是有了,那需要有個地方放妙計啊,放錦囊裡:

Java代碼  

  1. package com.yangguangfu.strategy;  
  2. public class Context {  
  3.     private IStrategy strategy;  
  4.     //構造函數,要你使用哪個妙計  
  5.     public Context(IStrategy strategy){  
  6.         this.strategy = strategy;  
  7.     }  
  8.     public void operate(){  
  9.         this.strategy.operate();  
  10.     }  
  11. }  

然後就是趙雲雄赳赳的揣着三個錦囊,拉着已步入老年行列,還想着娶純情少女的,色咪咪的劉備老爺子去入贅了,嗨,還别說,亮哥的三個妙計還真不錯,瞧瞧:

Java代碼  

  1. package com.yangguangfu.strategy;  
  2. public class ZhaoYun {  
  3.     public static void main(String[] args) {  
  4.         Context context;  
  5.         //剛到吳國的時候拆開第一個  
  6.         System.out.println("----------剛剛到吳國的時候拆開第一個---------------");  
  7.         context = new Context(new BackDoor());  
  8.         context.operate();//拆開執行  
  9.         System.out.println("\n\n\n\n\n\n\n\n\n\n\n\n\n");  
  10.         //當劉備樂不思蜀時,拆開第二個  
  11.         System.out.println("----------劉備樂不思蜀,拆第二個了---------------");  
  12.         context = new Context(new GivenGreenLight());  
  13.         context.operate();//拆開執行  
  14.         System.out.println("\n\n\n\n\n\n\n\n\n\n\n\n\n");  
  15.         //孫權的小追兵了,咋辦?拆開第三個錦囊  
  16.         System.out.println("----------孫權的小追兵了,咋辦?拆開第三個錦囊---------------");  
  17.         context = new Context(new BlackEnemy());  
  18.         context.operate();//拆開執行  
  19.         System.out.println("\n\n\n\n\n\n\n\n\n\n\n\n\n");  
  20.     }  
  21. }  

       後話:就這三招,搞得的周郎是“賠了夫人又折兵”呀!這就是政策模式,高内聚低耦合的特點也表現出來了,還有一個就是擴充性,也就是OCP原則,政策類可以繼續添加下去,隻是修改Context.java就可以了,這個不多說了,自己領會吧。

6 什麼情況下使用政策設計模式

     (1) 如果在一個系統裡有許多類,他們之間的差別僅在于他們的行為,那麼使用政策設計模式可以動态的讓 一個對象在許多行為中選擇一種行為。

     (2) 一個系統需要動态地在幾種算法中選擇一種,那麼這些算法可以包裝到一個個的具體算法類裡,而這些 具體算法類都是一個抽象算法的子類。換言之,這些具體算反類均有同一接口,由于多态性原則,用戶端可以選擇使用任何一個具體算法類,并持有一個資料類型是抽象算法類的對象。

    (3) 一個系統的算法使用的資料不可以讓用戶端知道。政策設計模式可以避免讓用戶端涉及到不必要接觸到與算法相關的負責資料。

    (4)如果一個對象有很多的行為,如果設計的不好的話,這些行為就隻好使用多重if-else的條件選擇語句來實作。

    如果此時使用政策設計模式,把這些行為轉移動相應的具體政策裡面,就可以避免使用難于維護的多重條件選擇語句,并展現面向對象的設計概念。 

7 政策設計模式的優點和缺點

  優點:

   (1) 政策模式提供了管理相關的算法的辦法。政策類的等級結構定義了一個算法或行為族。恰當使用繼承可以把公共的代碼移動父類裡面,進而避免重複的代碼。

   (2) 政策模式提供了可以替換繼承關系的辦法。繼承可以處理多種算法或行為。如果不是政策設計模式,那麼使用算法或行為的環境類 就可能會有一些子類,每一個子類提供一個不同的算法或行為,但是這樣一來算法或行為的使用者就和算法或行為混合在一起,進而不可能再獨立演化。繼承使得動态改變算法或行為變得不可能。

   (3) 使用政策模式可以避免使用多重條件轉移語句。多重轉移語句不易維護,它把算法邏輯或行為混合在一起,這樣比使用繼承或實作接口的方法相比太原始、太落後了。

缺點:

   (1)用戶端必須知道所有的政策類,并自行決定使用一個政策。這就意味着用戶端必須了解這些算法的差別,以便适時選擇恰當的算法類。換言之,政策模式隻适用于知道所有的算法或行為的情況。

   (2) 政策模式會造成很多的政策類。有時候可以通過依賴于環境的狀态儲存到用戶端裡面,而将政策設計成共享的,這裡政策類執行個體可以被不同用戶端使用。換言之,可以使用享遠模式來減少對象的數量。

繼續閱讀