閑言
最近鄙人在看《設計模式之禪》這本書峰搪,鞏固一下常用的設計模式届案,本文的例子就直接用的書中的例子,因為作者寫的通俗易懂罢艾,讓我看的欲罷不能楣颠,給作者大大比心!8莉恰(其實我就是懶)
工廠模式的優(yōu)點自不必說童漩,首先,良好的封裝性春锋,在使用的時候我們不必考慮對象創(chuàng)建的各種約束條件矫膨,只需要知道要生產的產品的類名就可以了。其次期奔,優(yōu)秀的可拓展性侧馅,如果業(yè)務有變化,需要增加或者刪除一個產品類呐萌,只需要修改工廠類就可以了馁痴,做到了真正的擁抱變化。最后肺孤,工廠模式是典型的解耦框架罗晕,符合迪米特法則,也符合依賴倒置的原則赠堵。
1.工廠模式定義
工廠模式在我們日常開發(fā)中式使用頻率非常高的一種設計模式小渊,其定義為:定義一個用于創(chuàng)建對象的接口,讓子類決定創(chuàng)建那個類茫叭,該模式使一個類的實例化延遲到其子類酬屉。
也就是說我們創(chuàng)建一個接口,用這個接口去生產具體的類揍愁,不用關心類是怎么創(chuàng)建的呐萨,如何初始化,只須關心要生產的是具體哪一個類吗垮,至于如何創(chuàng)建垛吗,我們去交給工廠來實現(xiàn)。
2.通用實現(xiàn)
以上圖女媧造人為例烁登,我們現(xiàn)在要生產出具體膚色的人怯屉,先創(chuàng)建一個接口AbstractHumanFactory,用于規(guī)定工廠中創(chuàng)建人類的方法饵沧,再創(chuàng)建一個人類的接口锨络,里面規(guī)定了無論那種膚色的人都有的方法,膚色和語言狼牺,方法的具體實現(xiàn)由下面具體膚色的人來實現(xiàn)羡儿。下面上代碼:
//抽象工廠類
public abstract class AbsFactory {
public abstract <T extends Human>T createHuman(Class<T> cls);
}
//人類接口
interface Human {
void getColor();
void talk();
}
//工廠類
public class FactoryImpl extends AbsFactory{
@Override
public <T extends Human> T createHuman(Class<T> cls) {
Human human=null;
try {
human=(T)Class.forName(cls.getName()).newInstance();
} catch (Exception e) {
System.out.println("創(chuàng)建人類失敗");
}
return (T)human;
}
}
//黑人
public class BlackHuman implements Human{
@Override
public void getColor() {
System.out.println("我是黑種人,我的皮膚是黑色的是钥。");
}
@Override
public void talk() {
System.out.println("一般人聽不懂黑人在說什么掠归。");
}
}
//黃種人
public class YellowHuman implements Human{
@Override
public void getColor() {
System.out.println("我是黃種人缅叠,我的皮膚是黃色的。");
}
@Override
public void talk() {
System.out.println("我們黃種人說的一般都是雙字節(jié)");
}
}
//白人
public class WhiteHuman implements Human{
@Override
public void getColor() {
System.out.println("我是白種人虏冻,我的皮膚是白色的肤粱。");
}
@Override
public void talk() {
System.out.println("白種人說的一般都是單字節(jié)。");
}
}
下面是場景類厨相,也就是我們的使用場景:
public class NvWa {
public static void main(String[] args) {
AbsFactory factory=new FactoryImpl();
Human white=factory.createHuman(WhiteHuman.class);
white.getColor();
white.talk();
Human yellow=factory.createHuman(YellowHuman.class);
yellow.getColor();
yellow.talk();
Human black=factory.createHuman(BlackHuman.class);
black.getColor();
black.talk();
}
}
運行結果:
我是白種人领曼,我的皮膚是白色的。
白種人說的一般都是單字節(jié)蛮穿。
我是黃種人庶骄,我的皮膚是黃色的。
我們黃種人說的一般都是雙字節(jié)
我是黑種人践磅,我的皮膚是黑色的单刁。
一般人聽不懂黑人在說什么。
Process finished with exit code 0
以上就是工廠模式的通用實現(xiàn)音诈。
3.簡單工廠模式
簡單工廠示UML圖
在類圖中幻碱,我們把AbsstractHumanFactory刪除,同時把HumanFactory中的createHuman方法修改成靜態(tài)方法细溅,而在我們的場景類NvWa中也要做相應修改褥傍。
//工廠類
public class FactoryImpl{
public static <T extends Human> T createHuman(Class<T> cls) {
Human human=null;
try {
human=(T)Class.forName(cls.getName()).newInstance();
} catch (Exception e) {
System.out.println("創(chuàng)建人類失敗");
}
return (T)human;
}
}
//場景類
public class NvWa {
public static void main(String[] args) {
Human white=FactoryImpl.createHuman(WhiteHuman.class);
white.getColor();
white.talk();
Human yellow=FactoryImpl.createHuman(YellowHuman.class);
yellow.getColor();
yellow.talk();
Human black=FactoryImpl.createHuman(BlackHuman.class);
black.getColor();
black.talk();
}
}
運行結果:
我是白種人,我的皮膚是白色的喇聊。
白種人說的一般都是單字節(jié)恍风。
我是黃種人,我的皮膚是黃色的誓篱。
我們黃種人說的一般都是雙字節(jié)
我是黑種人朋贬,我的皮膚是黑色的。
一般人聽不懂黑人在說什么窜骄。
簡單工廠的應用場景:當一個模塊只需要一個工廠類锦募,沒有必要把他生產出來,使用靜態(tài)方法就可以了邻遏。
這句話是書上的原話糠亩,其實我是沒怎么看懂,但是后來看到后面還有多工廠模式准验,我就明白了赎线。有時候,業(yè)務比較復雜糊饱,很多產品的創(chuàng)建方式垂寥,對對象的屬性值得初始化都不相同,如果都放到一個工廠中去,會使代碼結構不清晰滞项,所以我們?yōu)槊恳粋€產品(或創(chuàng)建方式一致的一類產品)都定義一個工廠狭归,于是,多工廠模式誕生了蓖扑。如果業(yè)務邏輯比較簡單的時候唉铜,一個工廠就可以搞定所有產品的生產的時候,我們就用簡單工廠模式律杠。下面我們來學習一下工廠模式的另一個變種。
4.多工廠模式
我們在AbstractHumanFactory中的抽象方法中去掉了傳參竞惋,因為每一個具體的工廠的職責都非常明確柜去,創(chuàng)建自己負責的產品類對象。女媧類也需要做相應修改拆宛。
public abstract class AbsFactory {
public abstract <T extends Human>T createHuman();
}
public class BlackHumanFactory extends AbsFactory{
@Override
public Human createHuman() {
return new BlackHuman();
}
}
public class WhiteHumanFactory extends AbsFactory{
@Override
public Human createHuman() {
return new WhiteHuman();
}
}
public class YellowHumanFactory extends AbsFactory{
@Override
public Human createHuman() {
return new YellowHuman();
}
}
public class NvWa {
public static void main(String[] args) {
Human white=(new WhiteHumanFactory()).createHuman();
white.getColor();
white.talk();
Human yellow=(new YellowHumanFactory()).createHuman();
yellow.getColor();
yellow.talk();
Human black=(new BlackHumanFactory()).createHuman();
black.getColor();
black.talk();
}
}
運行結果和上面一樣嗓奢,這里不再展示。