02-工厂模式

工厂模式

前言

工厂模式是设计模式中对我困扰最多的一个设计模式。网上有很多博客在讲工厂模式有三种(简单工厂、工厂方法和抽象工厂),代码也很简单,但是我就一直搞不懂为什么要有个工厂方法模式,以及工厂方法模式在所谓的开闭原则下面相比简单工厂的优点。

现在大致明白了,为了解耦,接下来介绍各个工厂模式的实现以及优缺点。文中代码示例可以去github查看。

介绍

工厂模式分三类:

  • 简单工厂模式:创建产品接口,具体产品实现该接口,工厂类对象负责根据参数生成不同类型的产品
  • 工厂方法模式:对简单工厂中的工厂类进一步抽象为接口。
  • 抽象工厂模式:相比工厂方法模式,多了个产品族的概念,工厂接口中有多个方法创建不同的产品。

个人认为工厂方法模式和抽象工厂模式都是抽象工厂模式。顾名思义,抽象工厂不就是把工厂类抽象成接口。只不过工厂方法是只能创建一个产品,抽象工厂可以创建多个产品。

简单工厂模式

简单工厂不算设计模式,应该算是一个代码优化,日常写代码的时候我们也会写出来类似的。总而言之,他是根据参数类型生成不同类型的产品的一个类。比如我们定义一个鼠标工厂,根据传入的参数决定生产哪种类型的鼠标:0生成联想,1生成戴尔,2生成罗技,罗技鼠标是真的好用。

简单工厂由抽象产品接口、具体产品类和产品工厂三部分组成。产品工厂负责根据传递参数制造不同的对象。

在这里插入图片描述

代码示例

/**
 * 鼠标接口
 */
public interface Mouse {
    String getName();

    Integer getPrice();

    default void print() {
        System.out.println("鼠标名称:" + getName() + ",鼠标价格:" + getPrice());
    }
}
/**
 * 戴尔鼠标
 */
public class DellMouse implements Mouse {


    @Override
    public String getName() {
        return "戴尔鼠标";
    }

    @Override
    public Integer getPrice() {
        return 50;
    }
}
/**
 * 惠普鼠标
 */
public class HpMouse implements Mouse {


    @Override
    public String getName() {
        return "惠普鼠标";
    }

    @Override
    public Integer getPrice() {
        return 10;
    }
}
/**
 * 罗技鼠标
 */
public class LogiMouse implements Mouse {


    @Override
    public String getName() {
        return "罗技鼠标";
    }

    @Override
    public Integer getPrice() {
        return 100;
    }
}
/**
 * 鼠标工厂类
 */
public class MouseFactory {

    public static Mouse createMouse(Integer type) throws IllegalAccessException {
        assert type != null;
        switch (type) {
            case 0:
                return new HpMouse();
            case 1:
                return new DellMouse();
            case 2:
                return new LogiMouse();
            default:
                throw new IllegalAccessException("参数异常");
        }
    }
}
public void simpleFactoryTest() throws IllegalAccessException {
        Mouse mouse = MouseFactory.createMouse(0);
        mouse.print();
        Mouse mouse1 = MouseFactory.createMouse(1);
        mouse1.print();
        Mouse mouse2 = MouseFactory.createMouse(2);
        mouse2.print();
    }

优缺点

优点:较另外两个工厂模式而言,代码简洁明了。工厂类对象提供了一个根据类型选择创建对象的方法。

缺点:工厂类对象耦合性高,破坏了开闭原则,当需要添加一个新产品时,工厂类对象要做修改。

工厂方法和抽象工厂模式

我们将工厂方法和抽象工厂合并到一块讲解,因为从代码结构上来看,他们两个是一样的,只不过抽象工厂方法工厂中有多个方法,可以创建多个产品。

工厂方法模式

简单工厂每次添加新产品的时候需要新增产品类,并且在工厂类中增加对应的代码逻辑。将简单工厂模式再次优化,对工厂类抽象成接口,具体工厂生产具体产品。新增产品时,只需要新增对应工厂,无需修改原有工厂代码。

简单工厂由抽象产品接口、具体产品类、抽象工厂接口和具体工厂组成,工厂和产品相对应。
在这里插入图片描述

代码示例
//抽象工厂接口
public interface Factory {
     Mouse createMouse();
}
// 戴尔工厂类
import com.hello.designPattern.FactoryPattern.interfaces.Factory;
import com.hello.designPattern.FactoryPattern.interfaces.Mouse;
import com.hello.designPattern.FactoryPattern.model.DellMouse;

public class DellFactory implements Factory {
    @Override
    public Mouse createMouse() {
        return new DellMouse();
    }
}
// 惠普工厂类
public class HpFactory implements Factory {
    @Override
    public Mouse createMouse() {
        return new HpMouse();
    }
}
// 罗技工厂类
public class LogiFactory implements Factory {
    @Override
    public Mouse createMouse() {
        return new LogiMouse();
    }
}
// 测试方法
 @Test
    public void factoryMethodTest(){
        Mouse hoMouse = new HpFactory().createMouse();
        Mouse dellMouse = new DellFactory().createMouse();
        Mouse logiMouse = new LogiFactory().createMouse();
        hoMouse.print();
        dellMouse.print();
        logiMouse.print();
    }

抽象工厂模式

接下来问题就来了,工厂不仅造鼠标,还造键盘,代码就需要在工厂接口中添加一个创建键盘的一个方法,这个时候,工厂方法模式就变成了抽象工厂模式。

抽象工厂模式代码就不在文中体现了,跟工厂方法模式基本上一样,添加了一个键盘接口,实现了惠普键盘、戴尔键盘和罗技键盘三个对象,然后在工厂类接口中添加创建键盘的方法,各工厂实现该方法。具体代码可见github

在这里插入图片描述

总结

在工作中,简单工厂适用于大部分业务逻辑不复杂的场景,代码少,类少,简单粗暴。如果需求较为复杂,并且时常变更,那就用工厂方法或抽象工厂。

参考链接

菜鸟工厂模式

java的三种工厂模式

抽象工厂模式和工厂模式的区别?

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值