最近在学习设计模式,结合了一下其它博客的观点,按照了自己的理解与实现,将自己的想法表达出来,以比较简单的易懂的方式写出来,作为自己学习的输出,内容不是十分全面,希望帮助你们通过这里快速了解大概的思想,之后再做进一步学习。
本文分为三部分:
- 简单工厂模式;
- 工厂方法模式;
- 抽象工厂模式
一、简单工厂模式
在介绍简单工厂模式之前,先来假设一下:
我们作为顾客,我们需要得到书这样一个物品。
于是,我们写出以下代码:
public interface Book {
public void typeOfBook();
}
class EnglishBook implements Book{
@Override
public void typeOfBook() {
System.out.println("我是一本英语书");
}
}
class MathBook implements Book{
@Override
public void typeOfBook() {
System.out.println("我是一本数学书");
}
}
这是顾客需要执行的操作:
public class Client {
public static void main(String[] args) {
Book b1 = new EnglishBook();
Book b2 = new MathBook();
b1.typeOfBook();
b2.typeOfBook();
}
}
在上述情况下,顾客需要获得一本书就必须自己执行创建的过程,即顾客需要自己满足自己动手创建来满足自己的需要,这对用户不友好。
在这种情况下,我们有了简单工厂模式:
我们新建了一个BookFactory(或许叫BookStore,在这里我们假设BookFactory与BookStore一样都是生产书的地方),在这个工厂类里我们定义了顾客需要了样本书籍,根据顾客的需求来返回不同的书籍。
public class BookFactory {
public Book getBook(String bookType){
if ("EnglishBook".equals(bookType)){
return new EnglishBook();
}else if("MathBook".equals(bookType)){
return new MathBook();
}else{
return null;
}
}
}
或者也可以写成以下形式:
public class BookFactory {
public static Book getEnglishBook() {
return new EnglishBook();
}
public static Book getMathBook() {
return new MathBook();
}
}
public class Client {
public static void main(String[] args) {
Book englishBook = new BookFactory().getBook("EnglishBook");
Book mathBook = new BookFactory().getBook("MathBook");
englishBook.typeOfBook();
mathBook.typeOfBook();
}
}
现在这种情况就相当于书籍都集中一个叫BookFactory的地方来集中售卖书籍,顾客只需要到这个地方来并且传达想要得到的书籍的名称,这个地方就可以返回你的需要的对象。
优缺点说明:
- 优点:代码简单,容易实现
- 缺点:无法增加产品,增加产品需要修改原来的代码,会造成维护困难的后果,违背了设计模式的原则——OCP(开闭原则)。
二、工厂方法模式
工厂方法模式去掉了简单工厂模式中工厂方法的静态属性,使得它可以被子类继承。这样在简单工厂模式里集中在工厂方法上的压力可以由工厂方法模式里不同的工厂子类来分担。 :
//抽象产品类
public interface Book {
public void getBook();
}
//具体产品类
class EnglishBook implements Book{
@Override
public void getBook() {
System.out.println("我是一本英语书");
}
}
//具体产品类
class MathBook implements Book{
@Override
public void getBook() {
System.out.println("我是一本数学书");
}
}
//抽象工厂类
public interface BookFactory {
public Book createBook();
}
//具体工厂类(每个具体工厂负责一个具体产品)
class EnglishBookFactory implements BookFactory{
@Override
public Book createBook() {
return new EnglishBook();
}
}
//具体工厂类(每个具体工厂负责一个具体产品)
class MathBookFactory implements BookFactory{
@Override
public Book createBook() {
return new MathBook();
}
}
顾客在调用时直接找到该厂(每个具体工厂负责一个具体产品) ,该厂便会创建顾客需要的书籍:
//顾客
public class Client {
public static void main(String[] args) {
Book englishBook = new EnglishBookFactory().createBook();
Book mathBook = new MathBookFactory().createBook();
englishBook.getBook();
mathBook.getBook();
}
}
三、抽象工厂模式
抽象工厂模式是工厂方法模式的升级版本。
抽象工厂就是一个工厂不单生产一个种类的产品,而是生产多个种类的产品。
首先先简单说明一下族的概念,例如阿迪与耐克,阿迪有阿迪跑鞋、阿迪球服,耐克有耐克跑鞋、耐克球服,对于跑鞋的层面来说,他们就是一类产品,而耐克或是阿迪旗下的商品则可以叫做一个族。
假设我在这里分成cheap和expensive两个族,两个族都有各自的产品轮胎Tire和引擎Engine,我在创建对象的时候可根据族来选择我需要的族产品,再选择具体想要的产品。
//抽象产品类
public interface ITire {
public void tire();
}
//具体产品类
class cheapTire implements ITire{
@Override
public void tire() {
System.out.println("普通轮胎");
}
}
//具体产品类
class expensiveTire implements ITire{
@Override
public void tire() {
System.out.println("高级轮胎");
}
}
//抽象产品类
public interface IEngine {
public void engine();
}
//具体产品类
class cheapEngine implements IEngine{
@Override
public void engine() {
System.out.println("普通引擎");
}
}
//具体产品类
class expensiveEngine implements IEngine{
@Override
public void engine() {
System.out.println("高级引擎");
}
}
//抽象工厂类
public interface CarFactory {
public ITire createTire();
public IEngine createEngine();
}
//具体工厂类,按照族来分
class cheapCarFactory implements CarFactory{
@Override
public ITire createTire() {
return new cheapTire();
}
@Override
public IEngine createEngine() {
return new cheapEngine();
}
}
//具体工厂类,按照族来分
class expensiveCarFactory implements CarFactory{
@Override
public ITire createTire() {
return new expensiveTire();
}
@Override
public IEngine createEngine() {
return new expensiveEngine();
}
}
//顾客可以根据想要的族来创建该族中想要的产品
public class Client {
public static void main(String[] args) {
CarFactory carFactory1 = new cheapCarFactory();
carFactory1.createEngine().engine();
carFactory1.createTire().tire();
CarFactory carFactory2 = new expensiveCarFactory();
carFactory2.createTire().tire();
carFactory2.createEngine().engine();
}
}
总结
三种方式区别:
- 简单工厂模式:集合了工厂的实现在一个类里,如果需要修改产品需要修改原来的类,会造成扩展性差的问题。
- 工厂方法模式:改进了简单工厂模式的扩展性差的问题,使每个产品由每个具体的实现类单一负责,通过增加新的工厂类可以实现扩展。
- 抽象工厂模式:不可以增加产品,可以增加产品族。