Java 的靜态工廠模式和抽象工廠模式
- 1、靜态工廠模式
-
- 1.1、優缺點
- 1.2、實作案例
-
- 1.2.1、抽象類
- 1.2.2、實作類
- 1.2.3、靜态工廠類
- 1.2.4、測試類
- 2、抽象工廠模式
-
- 2.1、适用場景
- 2.2、案例介紹
-
- 2.2.1、抽象類
- 2.2.2、實作類
- 2.2.3、工廠類
- 2.2.4、測試類
1、靜态工廠模式
靜态工廠模式,在平常開發中是比較常見的。
1.1、優缺點
- 優點:
- 将建立執行個體的工作與使用執行個體的工作分開,使用者不必關心類對象如何建立,明确了職責。
- 把初始化執行個體時的工作放到工廠裡進行,使代碼更容易維護。 更符合面向對象的原則,面向接口程式設計,而不是面向實作程式設計。
- 缺點:
- 由于工廠類集中了所有産品建立邏輯,一旦不能正常工作,整個系統都要受到影響。
- 要新增産品類的時候,就要修改工廠類的代碼,違反了開放封閉原則。即:對擴充的開放,對修改的關閉。
- 簡單工廠模式由于使用了靜态工廠方法,靜态方法不能被繼承和重寫,會造成工廠角色無法形成基于繼承的等級結構.
1.2、實作案例
- 代碼結構:
1.2.1、抽象類
package com.dsj.demo.staticfactory.service;
public abstract class FoodsService {
/**
* 烹饪
*/
public abstract void cook();
}
1.2.2、實作類
-
FishServiceImpl
package com.dsj.demo.staticfactory.service;
public class FishServiceImpl extends FoodsService {
@Override
public void cook() {
System.out.println("服務員,來一盤紅燒魚 !!!");
}
}
-
MeetServiceImpl
package com.dsj.demo.staticfactory.service;
/**
* @author Pengzf
*/
public class MeetServiceImpl extends FoodsService {
@Override
public void cook() {
System.out.println("服務員,來一盤紅燒肉 !!!");
}
}
1.2.3、靜态工廠類
-
StaticFactoryBeans
package com.dsj.demo.staticfactory;
import com.dsj.demo.staticfactory.service.FishServiceImpl;
import com.dsj.demo.staticfactory.service.FoodsService;
import com.dsj.demo.staticfactory.service.MeetServiceImpl;
public class StaticFactoryBeans {
public static FoodsService createFishBean () {
return new FishServiceImpl();
}
public static FoodsService createMeetBean() {
return new MeetServiceImpl();
}
}
1.2.4、測試類
package com.dsj.demo.staticfactory;
import com.dsj.demo.staticfactory.service.FoodsService;
public class TestStaticFactory {
public static void main(String[] args) {
FoodsService foodsService1 = StaticFactoryBeans.createFishBean();
foodsService1.cook();
FoodsService foodsService2 = StaticFactoryBeans.createMeetBean();
foodsService2.cook();
}
}
- 測試類執行結果如下:
服務員,來一盤紅燒魚 !!!
服務員,來一盤紅燒肉 !!!
2、抽象工廠模式
- 抽象工廠模式是指當有多個抽象角色時,使用的一種工廠模式。是所有形态的工廠模式中最為抽象和最具一般性的一種形态。
- 抽象工廠模式可以向用戶端提供一個接口,使用戶端在不必指定産品的具體的情況下,建立多個産品族中的産品對象。
2.1、适用場景
- 一個系統要獨立于它的産品的建立、組合和表示時。
- 一個系統要由多個産品系列中的一個來配置時。
- 需要強調一系列相關的産品對象的設計以便進行聯合使用時。
- 提供一個産品類庫,而隻想顯示它們的接口而不是實作時。
- 提供一個建立一系列相關或互相依賴對象的接口,而無需指定它們具體的類
2.2、案例介紹
該案例是多個産品族,每個産品族又存在多個不同産品的場景。實際工作中,可能隻有一個産品族,可根據實際場景,将該案例簡化使用。該案例所想表達的是抽象工廠的思想,具體可根據不同業務場景,酌情優化調整使用。
- 代碼結構:
2.2.1、抽象類
- 産品抽象類 (
)CarService
package com.dsj.demo.abstractfactory.service;
public abstract class CarService {
/**
* 駕駛
*/
public abstract void driver();
}
- 産品族抽象類 - 奧迪 (
)AudiService
package com.dsj.demo.abstractfactory.service;
public abstract class AudiService extends CarService {
/**
* 自我介紹
*/
public abstract void selfIntroduction();
}
- 産品族抽象類 - 沃爾沃 (
)VolvoService
package com.dsj.demo.abstractfactory.service;
public abstract class VolvoService extends CarService {
/**
* 售後
*/
public abstract void afterSale ();
}
2.2.2、實作類
- 奧迪系列 - A4 (
)AudiA4ServiceImpl
package com.dsj.demo.abstractfactory.service;
public class AudiA4ServiceImpl extends AudiService{
@Override
public void driver() {
System.out.println("駕駛奧迪A4 !!!");
}
@Override
public void selfIntroduction() {
System.out.println("這裡是奧迪A4 !!!");
}
}
- 奧迪系列 - A6 (
)AudiA6ServiceImpl
package com.dsj.demo.abstractfactory.service;
public class AudiA6ServiceImpl extends AudiService{
@Override
public void driver() {
System.out.println("駕駛奧迪A6 !!!");
}
@Override
public void selfIntroduction() {
System.out.println("這裡是奧迪A6 !!!");
}
}
- 沃爾沃系列 - S90(
)VolvoS90ServiceImpl
package com.dsj.demo.abstractfactory.service;
public class VolvoS90ServiceImpl extends VolvoService {
@Override
public void driver() {
System.out.println("駕駛 沃爾沃 S90, 倍爽!!!");
}
@Override
public void afterSale() {
System.out.println("沃爾沃 S90, 為您提供尊貴售後服務!!!");
}
}
- 沃爾沃系列 - XC60(
)VolVoXC60ServiceImpl
package com.dsj.demo.abstractfactory.service;
public class VolVoXC60ServiceImpl extends VolvoService {
@Override
public void driver() {
System.out.println("駕駛沃爾沃 XC60,倍爽!");
}
@Override
public void afterSale() {
System.out.println("沃爾沃 XC60, 為您提供尊貴售後服務!!!");
}
}
2.2.3、工廠類
- 抽象工廠類 - (
)AbstractFactoryBean
package com.dsj.demo.abstractfactory;
import com.dsj.demo.abstractfactory.service.CarService;
public abstract class AbstractFactoryBean {
/**
*
* @param cl
* @return
* @throws ClassNotFoundException
* @throws IllegalAccessException
* @throws InstantiationException
*/
public abstract CarService getCarService(Class cl) throws ClassNotFoundException,
IllegalAccessException, InstantiationException;
}
- 産品族工廠類 - 奧迪(
)AudiFactoryBean
package com.dsj.demo.abstractfactory;
import com.dsj.demo.abstractfactory.service.AudiService;
public class AudiFactoryBean extends AbstractFactoryBean {
@Override
public AudiService getCarService(Class cl) throws IllegalAccessException, InstantiationException {
return (AudiService) cl.newInstance();
}
}
- 産品族工廠類 - 沃爾沃(
)VolvoFactoryBean
package com.dsj.demo.abstractfactory;
import com.dsj.demo.abstractfactory.service.VolvoService;
/**
* @author Pengzf
*/
public class VolvoFactoryBean extends AbstractFactoryBean {
@Override
public VolvoService getCarService(Class cl) throws IllegalAccessException, InstantiationException {
return (VolvoService) cl.newInstance();
}
}
- 超級工廠類
package com.dsj.demo.abstractfactory;
public class FactoryProducer {
public static AbstractFactoryBean getFactory(Class cl) throws IllegalAccessException, InstantiationException {
System.out.println("建立工廠:" + cl.getName());
return (AbstractFactoryBean) cl.newInstance();
}
}
2.2.4、測試類
package com.dsj.demo.abstractfactory;
import com.dsj.demo.abstractfactory.service.*;
public class TestAbstractFactory {
public static void main(String[] args) throws IllegalAccessException, InstantiationException,
ClassNotFoundException {
AbstractFactoryBean audiFactoryBean = FactoryProducer.getFactory(AudiFactoryBean.class);
AudiService audiAFourServiceImpl = (AudiService) audiFactoryBean.getCarService(AudiA4ServiceImpl.class);
audiAFourServiceImpl.driver();
audiAFourServiceImpl.selfIntroduction();
AudiService audiA6ServiceImpl = (AudiService) audiFactoryBean.getCarService(AudiA6ServiceImpl.class);
audiA6ServiceImpl.driver();
audiA6ServiceImpl.selfIntroduction();
System.out.println("--------------------------------------");
AbstractFactoryBean volvoFactoryBean = FactoryProducer.getFactory(VolvoFactoryBean.class);
VolvoService volvoS90ServiceImpl = (VolvoService) volvoFactoryBean.getCarService(VolvoS90ServiceImpl.class);
volvoS90ServiceImpl.driver();
volvoS90ServiceImpl.afterSale();
VolvoService volVoXC60ServiceImpl = (VolvoService)volvoFactoryBean.getCarService(VolVoXC60ServiceImpl.class);
volVoXC60ServiceImpl.driver();
volVoXC60ServiceImpl.afterSale();
}
}
- 測試類執行結果如下:
建立工廠:com.dsj.demo.abstractfactory.AudiFactoryBean
駕駛奧迪A4 !!!
這裡是奧迪A4 !!!
駕駛奧迪A6 !!!
這裡是奧迪A6 !!!
--------------------------------------
建立工廠:com.dsj.demo.abstractfactory.VolvoFactoryBean
駕駛 沃爾沃 S90, 倍爽!!!
沃爾沃 S90, 為您提供尊貴售後服務!!!
駕駛沃爾沃 XC60,倍爽!
沃爾沃 XC60, 為您提供尊貴售後服務!!!
.