初識(shí)設(shè)計(jì)模式之簡(jiǎn)單工廠模式、工廠方法模式、抽象工廠模式

  • 簡(jiǎn)單工廠模式

  • 工廠方法模式

  • 抽象工廠模式

? 工廠顧名思義就是生產(chǎn)產(chǎn)品的意思,根據(jù)產(chǎn)品是具體產(chǎn)品還是具體工廠可分為簡(jiǎn)單工廠模式和工廠方法模式,根據(jù)工廠的抽象程度可分為工廠方法模式和抽象工廠模式。該模式用于封裝和管理對(duì)象的創(chuàng)建,是一種創(chuàng)建型模式。

1. 簡(jiǎn)單工廠模式

? 首先,我們有一個(gè)服裝制造廠,有一張服裝設(shè)計(jì)原稿?,F(xiàn)在,我們需要根據(jù)各個(gè)經(jīng)銷商的要求制造出不同顏色的衣服。

  • Clothes接口:即服裝設(shè)計(jì)原稿

    public interface Clothes {
      void getName();
    }
    
  • BlueClothes類:根據(jù)圖紙制造出來(lái)的藍(lán)色的衣服

    public class BlueClothes implements Clothes{
      public void getName() {
          System.out.print("BlueClothes");
      }
    }
    
  • RedClothes類:根據(jù)圖紙制造出來(lái)的藍(lán)色的衣服

    public class RedClothes implements Clothes{
      public void getName() {
          System.out.print("RedClothes");
      }
    }
    
  • GreenClothes類:根據(jù)圖紙制造出來(lái)的藍(lán)色的衣服

    public class GreenClothes implements Clothes{
      public void getName() {
          System.out.print("GreenClothes");
      }
    }
    
  • SimpleClothesFactory類:一個(gè)簡(jiǎn)單的服裝制造廠

    public class SimpleClothesFactory {
        public Clothes CreateClothes(String orderColor) {
               Clothes Clothes = null;
               if (orderColor.equals("blue")) {
                      Clothes = new BlueClothes();
               } else if (orderColor.equals("red")) {
                      Clothes = new RedClothes();
               } else if (orderColor.equals("green")) {
                      Clothes = new GreenClothes();
               }
               return Clothes;
        }
        //開工開工
        public static void main(String[] args) {
          SimpleClothesFactory scf = new SimpleClothesFactory();
          scf.CreateClothes("red").getName();
            //拿到紅色的訂單后,輸出"RedClothes"
        }
    }
    
    

    簡(jiǎn)單工廠模式的優(yōu)點(diǎn):

    • 工廠類是整個(gè)模式的關(guān)鍵。包含了必要的邏輯判斷,根據(jù)外界給定的信息,決定究竟應(yīng)該創(chuàng)建哪個(gè)具體類的對(duì)象。通過(guò)使用工廠類,外界可以從直接創(chuàng)建具體產(chǎn)品對(duì)象的尷尬局面擺脫出來(lái),僅僅需要負(fù)責(zé)“消費(fèi)”對(duì)象就可以了。而不必管這些對(duì)象究竟如何創(chuàng)建及如何組織的。明確了各自的職責(zé)和權(quán)利,有利于整個(gè)軟件體系結(jié)構(gòu)的優(yōu)化。

    簡(jiǎn)單工廠模式的缺點(diǎn):

    • 由于工廠類集中了所有實(shí)例的創(chuàng)建邏輯,違反了高內(nèi)聚責(zé)任分配原則,將全部創(chuàng)建邏輯集中到了一個(gè)工廠類中;它所能創(chuàng)建的類只能是事先考慮到的,如果需要添加新的類,則就需要改變工廠類了。
    • 當(dāng)系統(tǒng)中的具體產(chǎn)品類不斷增多時(shí)候,可能會(huì)出現(xiàn)要求工廠類根據(jù)不同條件創(chuàng)建不同實(shí)例的需求。這種對(duì)條件的判斷和對(duì)具體產(chǎn)品類型的判斷交錯(cuò)在一起,很難避免模塊功能的蔓延,對(duì)系統(tǒng)的維護(hù)和擴(kuò)展非常不利。
    • 這些缺點(diǎn)在工廠方法模式中得到了一定的克服。

    可以考慮的應(yīng)用場(chǎng)景:

    • 工廠類負(fù)責(zé)創(chuàng)建的對(duì)象比較少;
    • 客戶只知道傳入工廠類的參數(shù),對(duì)于如何創(chuàng)建對(duì)象(邏輯)不關(guān)心;
    • 由于簡(jiǎn)單工廠很容易違反高內(nèi)聚責(zé)任分配原則,因此一般只在很簡(jiǎn)單的情況下應(yīng)用。

2. 工廠方法模式

? 那么問(wèn)題來(lái)了,在我們使用簡(jiǎn)單工廠模式時(shí),當(dāng)我們的服裝廠生意做大了,吸引了無(wú)數(shù)經(jīng)銷商前來(lái)訂單,這時(shí)我們廠里只能生產(chǎn)紅、綠、藍(lán)顏色的衣服。如果我們想要接下這批訂單,那我們就要對(duì)原工廠進(jìn)行改造,那就會(huì)消耗大量的人力物力了。這時(shí),工廠方法模式就登場(chǎng)了!

  • Clothes接口:服裝設(shè)計(jì)原稿

  • YellowClothes類:按稿件設(shè)計(jì)出來(lái)的黃色衣服

  • WhiteClothes類:按稿件設(shè)計(jì)出來(lái)的白色衣服

  • ClothesFactory接口:服裝廠原型,建造具體服裝廠時(shí)的標(biāo)準(zhǔn)

  • YellowClothesFactory類:生產(chǎn)黃色衣服的工廠

  • WhiteClothesFactory類:生產(chǎn)白色衣服的工廠

  • Work類:工廠開工(啟動(dòng)類)

    interface Clothes{
        void showTag();
    }
    
    class YellowClothes implements Clothes{
      public void showTag() {
          System.out.println("YellowClothes");
      }
    }
    
    class WhiteClothes implements Clothes{
      public void showTag() {
          System.out.println("WhiteClothes");
      }
    }
    
    interface ClothesFactory{
        public abstract Clothes produce();
    }
    
    class YellowClothesFactory implements ClothesFactory{
      public Clothes produce() {
          return new YellowClothes();
      }
    }
    
    class WhiteClothesFactory implements ClothesFactory{
      public Clothes produce() {
          return new WhiteClothes();
      }
    }
    
    public class Work {
      public static void main(String[] args){
          ClothesFactory ycf = new YellowClothesFactory();
          ycf.produce().showTag();
          //輸出YellowClothes
          ClothesFactory wcf = new WhiteClothesFactory();
            wcf.produce().showTag();
            //輸出WhiteClothes
        }
    }
    

? 如此這般,在我們接受到新訂單時(shí)我們只需要新建一個(gè)小工廠就可以了。不需要對(duì)建好的工廠進(jìn)行改造。它能更好的符合開閉原則的要求。

工廠方法模式的優(yōu)點(diǎn):

  • 用戶只需要關(guān)心產(chǎn)品對(duì)應(yīng)的工廠,甚至無(wú)需關(guān)心創(chuàng)建細(xì)節(jié)或具體產(chǎn)品類的類名。
  • 基于工廠角色和產(chǎn)品的多態(tài)性設(shè)計(jì)是工廠模式的關(guān)鍵。它能自主決定如何創(chuàng)建哪種產(chǎn)品對(duì)象,而創(chuàng)建細(xì)節(jié)都封裝在具體工廠內(nèi)部。
  • 在系統(tǒng)要添加新的產(chǎn)品時(shí),無(wú)需修改抽象工廠和抽象產(chǎn)品提供的接口,無(wú)需修改客戶端,也無(wú)需修改其他的具體工廠和具體產(chǎn)品,只要添加一個(gè)具體工廠和具體產(chǎn)品即可,從而提高系統(tǒng)的可擴(kuò)展性(符合開閉原則)

工廠方法模式的缺點(diǎn):

  • 在添加新產(chǎn)品時(shí),要編寫新的具體產(chǎn)品類,并要提供與之對(duì)應(yīng)的具體工廠類。系統(tǒng)軟件個(gè)數(shù)也成對(duì)增加,從而增加了系統(tǒng)的復(fù)雜度,帶來(lái)更多開銷。
  • 由于系統(tǒng)的可擴(kuò)展性,在客戶端中要引入抽象層進(jìn)行定義,從而增加了系統(tǒng)的抽象性和理解難度。

3. 抽象工廠模式

? 工廠模式中的每一個(gè)形態(tài)都是針對(duì)一定問(wèn)題的解決方案,工廠方法針對(duì)的是多個(gè)產(chǎn)品系列結(jié)構(gòu);而抽象工廠模式針對(duì)的是多個(gè)產(chǎn)品族結(jié)構(gòu),一個(gè)產(chǎn)品族內(nèi)有多個(gè)產(chǎn)品系列。

讓我們回到我們的服裝廠繼續(xù)分析,現(xiàn)在,我們已經(jīng)不滿足于衣服業(yè)務(wù)啦,我們要進(jìn)軍褲子生產(chǎn)屆,那么問(wèn)題來(lái)了,我們只有衣服生產(chǎn)廠,怎么辦呢?我們現(xiàn)在迫切需要一種多個(gè)產(chǎn)品族結(jié)構(gòu)的解決方案。

  • Clothes接口:衣服設(shè)計(jì)原稿

  • YellowClothes類:按稿件設(shè)計(jì)出來(lái)的黃色衣服

  • WhiteClothes類:按稿件設(shè)計(jì)出來(lái)的白色衣服

  • Trousers接口:褲子設(shè)計(jì)原稿

  • YellowTrousers類:按稿件設(shè)計(jì)出來(lái)的黃色褲子

  • WhiteTrousers類:按稿件設(shè)計(jì)出來(lái)的白色褲子

  • AbstractFactory抽象類:服裝廠原型,建造具體服裝廠時(shí)的標(biāo)準(zhǔn)

  • YellowFactory類:擁有黃色原料的工廠

  • WhiteFactory類:擁有白色原料的工廠

  • Work類:工廠開工(啟動(dòng)類)

    //衣服原稿
    interface Clothes{
        void showClothesTag();
    }
    //褲子原稿
    interface Trousers{
      void showTrousersTag();
    }
    
    //衣服原稿制作出來(lái)的黃色衣服
    class YellowClothes implements Clothes{
      public void showClothesTag() {
          System.out.println("YellowClothes");
      }
    }
    //衣服原稿制作出來(lái)的白色衣服
    class WhiteClothes implements Clothes{
      public void showClothesTag() {
          System.out.println("WhiteClothes");
      }
    }
    
    //衣服原稿制作出來(lái)的黃色褲子
    class YellowTrousers implements Trousers{
      public void showTrousersTag() {
          System.out.println("YellowTrousers");
      }
    }
    //衣服原稿制作出來(lái)的白色褲子
    class WhiteTrousers implements Trousers{
      public void showTrousersTag() {
          System.out.println("WhiteTrousers");
      }
    }
    
    //能生產(chǎn)衣服和褲子的工廠
    abstract class AbstractFactory{
      public abstract Clothes produceClothes();   
      public abstract Trousers produceTrousers();      
    }
    
    //擁有黃色原料的工廠
    class YellowFactory extends AbstractFactory{    
      public Clothes produceClothes() {        
          return new YellowClothes();    
      }    
      public Trousers produceTrousers() {        
          return new YellowTrousers();    
      }
    }
    //擁有白色原料的工廠
    class WhiteFactory extends AbstractFactory{    
      public Clothes produceClothes() {        
          return new WhiteClothes();    
      }    
      public Trousers produceTrousers() {        
          return new WhiteTrousers();    
      }
    }
    
    //啟動(dòng)類
    public class Work {
      public static void main(String[] args) {
          AbstractFactory yf = new YellowFactory();
          AbstractFactory wf = new WhiteFactory();
          System.out.println("黃色原料工廠正在生產(chǎn):");
          yf.produceClothes().showClothesTag();
          yf.produceTrousers().showTrousersTag();
          System.out.println("白色原料工廠正在生產(chǎn):");
          wf.produceClothes().showClothesTag();
          wf.produceTrousers().showTrousersTag();
      }
    }
    

    如此這般,我們就可以正式進(jìn)軍褲子制造屆啦。

    抽象工廠模式的優(yōu)點(diǎn):

    • 分離了具體的類。客戶通過(guò)抽象接口操縱實(shí)例,產(chǎn)品的類名也在具體工廠的實(shí)現(xiàn)中被分離,它們不出現(xiàn)在客戶代碼中。
    • 易于交換產(chǎn)品系列。一個(gè)具體工廠類只在初始化時(shí)出現(xiàn)一次,這使得改變一個(gè)應(yīng)用的具體工廠變得很容易,只需改變具體的工廠即可使用不同的產(chǎn)品配置。
    • 有利于產(chǎn)品的一致性。當(dāng)一個(gè)系列的產(chǎn)品對(duì)象被設(shè)計(jì)成一起工作時(shí),一個(gè)應(yīng)用一次只能使用同一個(gè)系列中的對(duì)象,這一點(diǎn)很重要,而抽象工廠很容易實(shí)現(xiàn)這一點(diǎn)。

    抽象工廠模式的缺點(diǎn):

    • 難以支持新種類的產(chǎn)品。因?yàn)槌橄蠊S接口確定了可以被創(chuàng)建的產(chǎn)品集合,所以難以擴(kuò)展抽象工廠以生產(chǎn)新種類的產(chǎn)品。

    可以考慮使用的場(chǎng)景:

    • 一個(gè)系統(tǒng)要獨(dú)立于它的產(chǎn)品的創(chuàng)建、組合和表示時(shí)。
    • 一個(gè)系統(tǒng)要由多個(gè)產(chǎn)品系列中的一個(gè)來(lái)配置時(shí)。
    • 需要強(qiáng)調(diào)一系列相關(guān)的產(chǎn)品對(duì)象的設(shè)計(jì)以便進(jìn)行聯(lián)合使用時(shí)。
    • 提供一個(gè)產(chǎn)品類庫(kù),而只想顯示它們的接口而不是實(shí)現(xiàn)時(shí)。

以上就是我對(duì)這三個(gè)模式的簡(jiǎn)單認(rèn)識(shí)啦,也是作為個(gè)人的學(xué)習(xí)總結(jié),僅供參考!

如有錯(cuò)誤,萬(wàn)望指正。

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容