前面介紹的工廠方法模式中考慮的是一類產(chǎn)品的生產(chǎn)精耐,如電視機(jī)廠只生產(chǎn)電視母廷,空調(diào)廠只生產(chǎn)空調(diào)。同種類稱為同等級隅熙,也就是說沐旨,工廠方法模式只生產(chǎn)同等級的產(chǎn)品,但是現(xiàn)實(shí)生活中許多工廠都是綜合型的工廠噪伊,能生產(chǎn)多等級(種類)的產(chǎn)品簿煌。如海爾、TCL等品牌既能生產(chǎn)電視機(jī)鉴吹,也能生產(chǎn)空調(diào)姨伟。
抽象工廠模式即是考慮多等級產(chǎn)品的生產(chǎn),將同一個(gè)具體工廠所生產(chǎn)的位于不同等級的一組產(chǎn)品稱為一個(gè)產(chǎn)品族豆励,海爾的電視機(jī)和海爾的空調(diào)屬于一個(gè)產(chǎn)品族夺荒,海爾的空調(diào)和TCL的空調(diào)屬于一個(gè)產(chǎn)品等級。
模式的定義與特點(diǎn)
抽象工廠(Abstract Factory)模式的定義:是一種為訪問類提供一個(gè)創(chuàng)建一組相關(guān)或相互依賴對象的接口良蒸,且訪問類無須指定所要產(chǎn)品的具體類就能得到同族的不同等級的產(chǎn)品的模式結(jié)構(gòu)技扼。
抽象工廠模式是工廠模式的升級版本,工廠方法模式只生產(chǎn)一個(gè)等級的產(chǎn)品嫩痰,而抽象工廠模式可以生產(chǎn)多個(gè)等級的產(chǎn)品淮摔。
使用抽象工廠模式一般要滿足以下條件。
- 系統(tǒng)中有多個(gè)產(chǎn)品族始赎,每個(gè)具體工廠創(chuàng)建同一族但屬于不同等級結(jié)構(gòu)的產(chǎn)品和橙。
- 系統(tǒng)一次只可能消費(fèi)其中某一族產(chǎn)品,即同族的產(chǎn)品一起使用造垛。
抽象工廠模式除了具有工廠方法模式的優(yōu)點(diǎn)外魔招,其他主要優(yōu)點(diǎn)如下。
- 可以在類的內(nèi)部對產(chǎn)品族中相關(guān)聯(lián)的多等級產(chǎn)品共同管理五辽,而不必專門引入多個(gè)新的類來進(jìn)行管理办斑。
- 當(dāng)需要產(chǎn)品族時(shí),抽象工廠可以保證客戶端始終只使用同一個(gè)產(chǎn)品的產(chǎn)品組。
- 抽象工廠增強(qiáng)了程序的可擴(kuò)展性乡翅,當(dāng)增加一個(gè)新的產(chǎn)品族時(shí)鳞疲,不需要修改原代碼,滿足開閉原則蠕蚜。
其缺點(diǎn)是:當(dāng)產(chǎn)品族中需要增加一個(gè)新的產(chǎn)品時(shí)尚洽,所有的工廠類都需要進(jìn)行修改。增加了系統(tǒng)的抽象性和理解難度靶累。
模式的結(jié)構(gòu)與實(shí)現(xiàn)
抽象工廠模式同工廠方法模式一樣腺毫,也是由抽象工廠、具體工廠挣柬、抽象產(chǎn)品和具體產(chǎn)品等 4 個(gè)要素構(gòu)成潮酒,但抽象工廠中方法個(gè)數(shù)不同,抽象產(chǎn)品的個(gè)數(shù)也不同⌒盎祝現(xiàn)在我們來分析其基本結(jié)構(gòu)和實(shí)現(xiàn)方法急黎。抽象工廠模式的主要角色如下:
- 抽象工廠(Abstract Factory):提供了創(chuàng)建產(chǎn)品的接口,它包含多個(gè)創(chuàng)建產(chǎn)品的方法 newProduct()侧到,可以創(chuàng)建多個(gè)不同等級的產(chǎn)品叁熔。如下CourseFactory
- 具體工廠(Concrete Factory):主要是實(shí)現(xiàn)抽象工廠中的多個(gè)抽象方法,完成具體產(chǎn)品的創(chuàng)建床牧。如下JavaCourseFactory荣回、PythonCourseFactory
- 抽象產(chǎn)品(Product):定義了產(chǎn)品的規(guī)范,描述了產(chǎn)品的主要特性和功能戈咳,抽象工廠模式有多個(gè)抽象產(chǎn)品心软。如下Video、Article
- 具體產(chǎn)品(ConcreteProduct):實(shí)現(xiàn)了抽象產(chǎn)品角色所定義的接口著蛙,由具體工廠來創(chuàng)建删铃,它同具體工廠之間是多對一的關(guān)系。如下JavaVideo踏堡、JavaArticle猎唁,PythonVideo、PythonArticle
如課程包含視頻和手記顷蟆,現(xiàn)有Java課程和Python課程诫隅,用抽象工廠模式實(shí)現(xiàn)如下:
代碼:
public abstract class Video {
public abstract void produce();
}
public abstract class Article {
public abstract void produce();
}
public class JavaVideo extends Video {
@Override
public void produce() {
System.out.println("錄制java課程視頻");
}
}
public class JavaArticale extends Article {
@Override
public void produce() {
System.out.println("編寫java課程手記");
}
}
public class PythonVideo extends Video {
@Override
public void produce() {
System.out.println("錄制python課程視頻");
}
}
public class PythonArticle extends Article {
@Override
public void produce() {
System.out.println("編寫python課程手記");
}
}
public interface CourseFactory {
Video getVideo();
Article getArticle();
}
public class JavaCourseFactory implements CourseFactory {
@Override
public Video getVideo() {
return new JavaVideo();
}
@Override
public Article getArticle() {
return new JavaArticale();
}
}
public class PythonCourseFactory implements CourseFactory {
@Override
public Video getVideo() {
return new PythonVideo();
}
@Override
public Article getArticle() {
return new PythonArticle();
}
}
public class Main {
public static void main(String[] args) {
CourseFactory courseFactory = new JavaCourseFactory();
Article article = courseFactory.getArticle();
Video video = courseFactory.getVideo();
article.produce();
video.produce();
}
}