天天看小說

第114章

小A:“什麼是簡單工廠模式?”

大B:“簡單工廠模式又叫靜態(tài)工廠模式,顧名思義,它是用來實例化目標類的靜態(tài)類。”

小A:“簡單工廠模式有什麼優(yōu)點?”

大B:“現(xiàn)在我就主要通過一個簡單的實例說明簡單工廠及其優(yōu)點。”

小A:“嗯。好。”

大B:“就如剛纔我講過的,有個國家的運動員協(xié)會。”

下面給出各個類的程序。

Code:[Copytoclipboard]

運動員.java

publicinterface運動員{

publicvoid跑();

publicvoid跳();

}

足球運動員.java

publicclass足球運動員implements運動員{

publicvoid跑(){

//跑啊跑

}

publicvoid跳(){

//跳啊跳

}

}

籃球運動員.java

publicclass籃球運動員implements運動員{

publicvoid跑(){

//donothing

}

publicvoid跳(){

//donothing

}

}

體育協(xié)會.java

publicclass體育協(xié)會{

publicstatic運動員註冊足球運動員(){

returnnew足球運動員();

}

publicstatic運動員註冊籃球運動員(){

returnnew籃球運動員();

}

}

俱樂部.java

publicclass俱樂部{

private運動員守門員;

private運動員後衛(wèi);

private運動員前鋒;

publicvoidtest(){

this前鋒=體育協(xié)會,註冊足球運動員();

this後衛(wèi)=體育協(xié)會,註冊足球運動員();

this守門員=體育協(xié)會,註冊足球運動員();

守門員,跑();

後衛(wèi),跳();

}

}

大B:“這就是簡單工廠模式的一個簡單實例,你應(yīng)該想象不用接口不用工廠而把具體類暴露給客戶端的那種混亂情形吧?就好像沒了體育總局,各個俱樂部在市場上自己胡亂的尋找仔細需要的運動員。簡單工廠就解決了這種混亂。我們用OCP看看簡單工廠,會發(fā)現(xiàn)如果要對系統(tǒng)進行擴展的話治需要增加實現(xiàn)產(chǎn)品接口的產(chǎn)品類(上例表現(xiàn)爲‘足球運動員’,‘籃球運動員’類,比如要增加個‘乒乓球運動員’類),而無需對原有的產(chǎn)品類進行修改。”

小A:“這咋一看好像滿足OCP。”

大B:“但是實際上還是需要修改代碼的——對,就是修改工廠類。上例中如果增加‘乒乓球運動員’產(chǎn)品類,就必須相應(yīng)的修改‘體育協(xié)會’工廠類,增加個‘註冊乒乓球運動員’方法。所以可以看出,簡單工廠模式是不滿足OCP的。”

小A:“那工廠方法模式哩?”

大B:“我們剛剛講了簡單工廠模式,下面繼續(xù)談?wù)劰S方法模式。剛纔點明瞭簡單工廠模式最大的缺點——不完全滿足OCP。爲了解決這一缺點,設(shè)計師們提出了工廠方法模式。工廠方法模式和簡單工廠模式最大的不同在於,簡單工廠模式只有一個(對於一個項目或者一個獨立模塊而言)工廠類,而工廠方法模式有一組實現(xiàn)了相同接口的工廠類。下面我們通過修改剛纔的實例來介紹工廠方法模式。我們在不改變產(chǎn)品類(‘足球運動員’類和‘籃球運動員’類)的情況下,修改下工廠類的結(jié)構(gòu)。”

相關(guān)代碼如下:

Code:[Copytoclipboard]

運動員.java

publicinterface運動員{

publicvoid跑();

publicvoid跳();

}

足球運動員.java

publicclass足球運動員implements運動員{

publicvoid跑(){

//跑啊跑

}

publicvoid跳(){

//跳啊跳

}

}

籃球運動員.java

publicclass籃球運動員implements運動員{

publicvoid跑(){

//donothing

}

publicvoid跳(){

//donothing

}

}

體育協(xié)會.java

publicinterface體育協(xié)會{

public運動員註冊();

}

足球協(xié)會.java

publicclass足球協(xié)會implements體育協(xié)會{

public運動員註冊(){

returnnew足球運動員();

}

}

籃球協(xié)會.java

publicclass籃球協(xié)會implements體育協(xié)會{

public運動員註冊(){

returnnew籃球運動員();

}

}

俱樂部.java

publicclass俱樂部{

private運動員守門員;

private運動員後衛(wèi);

private運動員前鋒;

publicvoidtest(){

體育協(xié)會中國足協(xié)=new足球協(xié)會();

this.前鋒=中國足協(xié),註冊();

this.後衛(wèi)=中國足協(xié),註冊();

守門員,跑();

後衛(wèi),跳();

}

}

大B:“很明顯可以看到,‘體育協(xié)會’工廠類變成了‘體育協(xié)會’接口,而實現(xiàn)此接口的分別是‘足球協(xié)會’‘籃球協(xié)會’等等具體的工廠類。”

小A:“這樣做有什麼好處呢?”

大B:“很明顯,這樣做就完全OCP了。如果需要再加入(或擴展)產(chǎn)品類(比如加多個‘乒乓球運動員’)的話就不再需要修改工廠類了,而只需相應(yīng)的再添加一個實現(xiàn)了工廠接口(‘體育協(xié)會’接口)的具體工廠類。”

小A:“工廠方法模式是爲了克服簡單工廠模式的缺點(主要是爲了滿足OCP)而設(shè)計出來的。但是,工廠方法模式就一定比簡單工廠模式好呢?”

大B:“不一定。1、結(jié)構(gòu)複雜度。從這個角度比較,顯然簡單工廠模式要佔優(yōu)。簡單工廠模式只需一個工廠類,而工廠方法模式的工廠類隨著產(chǎn)品類個數(shù)增加而增加,這無疑會使類的個數(shù)越來越多,從而增加了結(jié)構(gòu)的複雜程度。2、代碼複雜度。代碼複雜度和結(jié)構(gòu)複雜度是一對矛盾,既然簡單工廠模式在結(jié)構(gòu)方面相對簡潔,那麼它在代碼方面肯定是比工廠方法模式複雜的了。簡單工廠模式的工廠類隨著產(chǎn)品類的增加需要增加很多方法(或代碼),而工廠方法模式每個具體工廠類只完成單一任務(wù),代碼簡潔。3、客戶端編程難度。工廠方法模式雖然在工廠類結(jié)構(gòu)中引入了接口從而滿足了OCP,但是在客戶端編碼中需要對工廠類進行實例化。而簡單工廠模式的工廠類是個靜態(tài)類,在客戶端無需實例化,這無疑是個吸引人的優(yōu)點。4、管理上的難度。這是個關(guān)鍵的問題。我們先談擴展。衆(zhòng)所周知,工廠方法模式完全滿足OCP,即它有非常良好的擴展性。”

小A:“那是否就說明了簡單工廠模式就沒有擴展性呢?”

大B:“不是的。簡單工廠模式同樣具備良好的擴展性——擴展的時候僅需要修改少量的代碼(修改工廠類的代碼)就可以滿足擴展性的要求了。儘管這沒有完全滿足OCP,但不需要太拘泥於設(shè)計理論,要知道,sun提供的java官方工具包中也有好多沒有滿足OCP的例子啊(java.util.Calendar這個抽象類就不滿足OCP)。然後我們從維護性的角度分析下。假如某個具體產(chǎn)品類需要進行一定的修改,很可能需要修改對應(yīng)的工廠類。當同時需要修改多個產(chǎn)品類的時候,對工廠類的修改會變得相當麻煩(對號入座已經(jīng)是個問題了)。反而簡單工廠沒有這些麻煩,當多個產(chǎn)品類需要修改是,簡單工廠模式仍然僅僅需要修改唯一的工廠類。”

第51章第90章第44章第207章第199章第118章第127章第195章第228章第193章第121章第204章第129章第80章第186章第57章第58章第60章第157章第199章第213章第211章第195章第180章第77章第48章第19章第83章第76章第55章第53章第170章第178章第181章第99章第113章第205章第220章第123章第203章第94章第39章第176章第206章第41章第25章第96章第54章第11章第15章第200章第212章第64章第176章第138章第223章第205章第38章第197章第63章第118章第149章第127章第125章第20章第49章第23章第223章第182章第3章第214章第187章第34章第163章第117章第115章第44章第8章第130章第55章第152章第68章第64章第131章第49章第55章第200章第174章第127章第32章第86章第163章第226章第162章第80章第36章第124章第152章第39章
第51章第90章第44章第207章第199章第118章第127章第195章第228章第193章第121章第204章第129章第80章第186章第57章第58章第60章第157章第199章第213章第211章第195章第180章第77章第48章第19章第83章第76章第55章第53章第170章第178章第181章第99章第113章第205章第220章第123章第203章第94章第39章第176章第206章第41章第25章第96章第54章第11章第15章第200章第212章第64章第176章第138章第223章第205章第38章第197章第63章第118章第149章第127章第125章第20章第49章第23章第223章第182章第3章第214章第187章第34章第163章第117章第115章第44章第8章第130章第55章第152章第68章第64章第131章第49章第55章第200章第174章第127章第32章第86章第163章第226章第162章第80章第36章第124章第152章第39章
主站蜘蛛池模板: 松潘县| 湘阴县| 周至县| 铜川市| 中西区| 石狮市| 米易县| 浮山县| 东光县| 河西区| 杭锦旗| 星座| 新沂市| 肇源县| 全椒县| 修武县| 龙口市| 松原市| 延庆县| 宜州市| 庆云县| 铁岭市| 富川| 涟源市| 安西县| 江安县| 句容市| 云林县| 石棉县| 大埔县| 萍乡市| 红桥区| 正阳县| 沈阳市| 清镇市| 恭城| 台前县| 吉木乃县| 上饶县| 民丰县| 兰考县|