最近在學習設計模式的路上越走越遠...
今天主要記錄記錄一下學習的工廠模式。
1、由來
當我們創建一個對象,而這個對象的創建過程序紛繁復雜,可能導致大量的重復代碼的時候,工廠模式出現了。工廠方法模式通過定義一個單獨的創建對象的方法來解決這些問題。由子類實現這個方法來創建具體類型的對象。也就是說,在我們的實際運用中,工廠就是一個用來創建其他對象的對象。
2、實質
定義一個創建對象的接口,但讓實現這個接口的類來決定實例化哪個類。工廠方法讓類的實例化推遲到子類中進行。
3、現狀介紹
工廠模式目前有三個分支,簡單工廠模式,工廠方法模式和抽象工廠方法模式,其中,我主要學習的是抽象工廠方法模式,因為該方法是工廠模式中最高層的方法。簡單工廠模式,工廠類根據傳參不同得到不同的產品。工廠方法模式能夠創建這個系列中的各種產品,比如,iphone的各種配件。而抽象工廠模式作為更高級的模式,它可以創建整個蘋果公司各個產品流水線,比如,他可以創建生產iphone配件的工廠,可以創建生產ipad配件的工廠等等。那么,抽象工廠模式與工廠方法模式的最大區別就在於,工廠方法模式針對的是一個產品等級結構,它能夠創建這一個等級結構中的產品族;而抽象工廠模式則需要面對多個產品等級結構,也就是說,抽象工廠方法模式可以工廠方法模式中的工廠。
4、三分支的關系
簡單工廠模式通常伴隨着對象的具體類型與工廠具體類型的一一對應,客戶端代碼根據需要選擇合適的具體類型工廠使用。當這個選擇包含復雜的邏輯時,就可以創建一個單一的工廠類,用以包含這種選擇邏輯,根據參數的不同選擇實現不同的具體對象。這個工廠類不需要由每個具體產品實現一個自己的具體的工廠類,所以可以將工廠方法設置為靜態方法,這就有了工廠方法模式。而抽象工廠方法模式便是封裝着這樣一組有着共同主題的工廠方法模式中的工廠。
1、簡單工廠模式
當我們的主程序中需要自己手動初始化一個對象,但是我們並不想關注具體的初始化過程,這個時候簡單工廠模式就是您的選擇。
2、工廠方法模式
當你覺得傳入參數的這種簡單的工廠模式讓你程序容易出錯,並且程序中的if-else讓你的程序看起來有些臃腫,這個時候工廠方法模式就是您的選擇。
3、抽象工廠方法模式
當你工廠類需要修改時,而在工廠方法模式中需要修改原有的工廠類,這就違背了設計原則中的OCP(開放閉合原則),這個時候,抽象工廠方法模式就是您的選擇。
說不如做,看的再多不自己親手做一做來的有效率,這便是我學習工廠模式之后的心得。
首先,模擬場景。創建寶馬車,X6和5系的,那么首先的有一個抽象的汽車工廠,CarFactory,由它來生成X6和5系的工廠,一個汽車工廠生產出來的汽車至少得有個殼,發動機,變速箱啥的,所有就有了方法。創建CarFactory如下:
1 public interface CarFactory { 2 public CarFrame createCarFrame(); 3 public Engine createEngine(); 4 public Gearbox createGearbox(); 5 }
一個汽車的基本配件都出來了,那么所有的配件都應該有各自的接口,我們再分別創建Engine,Gearbox和CarFrame,Engine如下(Gearbox、CarFrame類似):
1 public interface Engine { 2 public void createEngine(); 3 4 }
然后我們的X6和5系的都應該有這些個接口吧,我們在分別創建他們各自的Engine,Gearbox和CarFrame,X6的Engine:
1 public class BwmXSixEngine implements Engine { 2 3 private String emissions; 4 5 public BwmXSixEngine(String emissions){ 6 7 this.emissions = emissions; 8 } 9 10 @Override 11 public void createEngine() { 12 System.out.println("this BWM XDrive engine,and emissions is "+ this.emissions); 13 } 14 }
5系的Engine:
1 public class BwmFiveSeriesEngine implements Engine { 2 3 private final String emissions; 4 5 public BwmFiveSeriesEngine(String emissions){ 6 this.emissions = emissions; 7 } 8 9 @Override 10 public void createEngine() { 11 System.out.println("this is BWMFiveSeriesEngine it's emissions of "+this.emissions); 12 } 13 }
現在,X6和5系就只差裝箱,我們就來創建他們的工廠吧,5系:
1 public class BwmFiveSeriesFactory implements CarFactory{ 2 3 4 @Override 5 public CarFrame createCarFrame() { 6 return new BwmFiveSeriesCarFrame("中大型車", new int[]{5047,1860,1491},"4門5座三廂車"); 7 } 8 9 @Override 10 public Engine createEngine() { 11 return new BwmFiveSeriesEngine("2.0T"); 12 } 13 14 @Override 15 public Gearbox createGearbox() { 16 return new BwmFIveSeriesGearbox("8擋手自一體"); 17 } 18 }
X6:
1 public class BwmXSixFactory implements CarFactory { 2 @Override 3 public CarFrame createCarFrame() { 4 return new BwmXSixCarFrame("中大型SUV",new int[]{4929,1983,1709},"5門5座SUV"); 5 } 6 7 @Override 8 public Engine createEngine() { 9 return new BwmXSixEngine("3.0T"); 10 } 11 12 @Override 13 public Gearbox createGearbox() { 14 return new BwmXSixGearbox("8擋手自一體"); 15 } 16 }
程序寫到這里也快結束了,我們自己在寫一個汽車超市來生成這些對象就好了,希望你有一次愉快的購物經歷,哈哈~
在抽象工廠模式的運用中,需要有一個總的抽象工廠,這個工廠制造可以生產具體東西的工廠類,比如,CarFactory和BwmXSixFactory之間的關系。然后就是接口的運用。接口對於高抽象層級的類有很大作用,站在高處便能規定對繼承該接口的類的行為,但並不具體到每一個繼承的類的行為。最后,工廠模式成功的隱藏了類的行為,滿足迪米特法則,調用者根本不關心怎么實現的,只要一個接口可以調用便行。
自己在設計模式這一塊還比較弱,以后還需多多學習。設計模式每一個都不是太難,重要的是各個擊破之后,將他們拿捏在手中能夠靈活的運用到實例的工作中。所以,重要的還是自己能力的提升,加油~
ps:文中若是有哪里理解不順或是需要改進的地方,望指出~
