2.3 Abstract Factory

Abstract factory的精神: 提供一個創造一系列相關或相互依賴物件的介面, 而無需指定它們具體的類別

  • AbstractFactory: 定義創造一系列產品物件的操作接口

  • ConcreteFactory: 實作抽象工廠定義的方法, 具體實作一系列產品物件的創造

  • AbstractProduct: 定義一類產品物件的介面

  • ConcreteProduct: 具體的產品實作物件, 通常在ConcreteFactory裡面, 會選擇具體的產品實作物件, 以創造符合抽象工廠定義的方法回傳的產品類型之物件.

  • Client: 主要使用抽象工廠來獲得一系列所需要的產品物件, 然後面對這些產品物件的介面編程, 以實作需要的功能.

  • 原始碼點我

認識抽象工廠

  • 功能: 抽象工廠是為一系列相關物件或相互依賴的物件建立一個介面. 從某種意義上來看, 這其實是一個產品系列, 或著是產品族

  • 實作成介面: AbstractFactory在Java中通常實作成介面, 不要被名稱誤導而以為是抽象類別了

  • 使用factory method: AbstractFactory定義了創造產品所需要的介面, 具體的實作是在實作類別裡面, 通常在實作類別中就需要選擇多種更具體的實作, 所以AbstractFactory定義的創造產品的方法可以看成是工廠方法, 而這些工廠方法的具體實作就延遲到了具體的工廠裡面. 也就是說使用工廠方法來實作抽象工廠

  • 切換產品族: 抽象工廠定義了一個產品族, 因此切換產品族的時候提供不同的抽象工廠即可

定義可擴展的工廠

  • 此範例中, 抽象工廠為每一種它能創造的產品物件都定義了相應的方法, 如創造CPU和主機板的方法等

  • 這種實作有個麻煩的地方就是若在產品族中要新增加一種產品, 如記憶體, 那就需要在抽象工廠裡添加創造記憶體的方法.當抽象工廠一發生變化, 所有的具體工廠實作都要發生變化, 這很不靈活

  • 現在有一種相對靈活, 但是不太安全的改進方式來解決此問題: 抽象工廠裡不需要定義那麼多方法, 定義一個方法即可,給這個方法設置一個參數, 通過這個參數來判斷具體要創造什麼產品物件; 由於只有一個方法,在回傳型別上就不能是具體的某個產品類型了, 只能是所有的產品物件都繼承或著實作的一個類型, 如讓所有的產品都實作某個介面, 或著乾脆使用Object類型

抽象工廠的優缺點

  • 分離介面與實作

  • 使切換產品族變得更容易

  • 不太容易擴展新的產品

  • 容易造成類別層次的複雜化

抽象工廠的本質: 選擇產品族的實作

何時選用

  • 如果希望一個系統獨立於其產品的創造、組合與表示時, 即希望一個系統只知道產品的介面, 而不關心實作的情況

  • 若一個系統要由多個產品系列中的一個來配置的時候, 換句話說, 就是可以動態切換產品族的時候

  • 要強調一系列相關產品的介面, 以便聯合使用它們之時

Last updated

Was this helpful?