Java源码阅读基础----设计模式----工厂模式

    前言:说到工厂大家都想到富士康,对不对。富士康大家都知道有什么功能,小米手机、苹果手机都是从里面生产出来的,也就是说工厂就是生产产品的,但是我们作为消费者,需要知道手机是怎么生产的吗?富士康除了生产手机还生产别的产品吗? 所以,工厂就是替消费者生产他们需要的产品,但却并不需要消费者知道怎么生产的,有哪些零部件,花了多少时间。
  • 简单工厂(Simple Factory):静态工厂方法
public interface Phone {

    String getName();
}

 
 
public class MiPhone implements Phone { 
    @Override 
    public String getName() { 
        return "小米手机"; 
    }
}
 
public class ApplePhone implements Phone {
    @Override
    public String getName() {
        return "苹果手机";
    }
}
    Phone 接口就代表工厂里生产手机的设备,无论你要生产小米手机还是苹果手机都需要这些手机设备
    MiPhone类就是工厂需要生产的手机
    ApplePhone类就是工厂需要生产的苹果手机。
 
public class SimpleFactory {

    public Phone getPhone(String name) throws Exception {
        if ("小米手机".equals(name)) {
            return new MiPhone();
        } else if ("苹果手机".equals(name)) {
            return new ApplePhone();
        } else {
            throw new Exception("对不起,我们不会生产该手机!");
        }
    }
}
    而SimpleFactory就是我们生产手机的“富士康”,我们会根据消费者需要购买什么样的手机,我们就会生产什么样d
public class SimpleFactoryTest {
    public static void main(String[] args) throws Exception {
        SimpleFactory simpleFactory = new SimpleFactory();
        System.out.println(simpleFactory.getPhone("小米手机").getName());
        System.out.println(simpleFactory.getPhone("苹果手机").getName());
        System.out.println(simpleFactory.getPhone("华为手机").getName());
    }
}
 
  
Connected to the target VM, address: '127.0.0.1:65019', transport: 'socket'
小米手机
苹果手机
Exception in thread "main" java.lang.Exception: 对不起,我们不会生产该手机! 
at com.design.pattern.factory.simple.SimpleFactory.getPhone(SimpleFactory.java:18) 
at com.design.pattern.factory.simple.SimpleFactoryTest.main(SimpleFactoryTest.java:11)
Disconnected from the target VM, address: '127.0.0.1:65019', transport: 'socket'
Process finished with exit code 1
但是我们从上面的例子可以看出,每当我们工厂需要生产新的手机时,我们就必须在工厂中修改我们的生产线(代码),才能生产新的手机,否则就会报错,这样就 不符合我们设计模式的6大原则之开闭原则

  • 工厂方法(Factory Method)
public interface PhoneFactory {
    Phone getPhone();
}
    PhoneFactory接口就是指我们工厂中每条流水线,每条流水线只生产一种手机。
public class MiPhoneFactory implements PhoneFactory {
    @Override
    public Phone getPhone() {
        return new MiPhone();
    }
}
public class ApplePhoneFactory implements PhoneFactory {
    @Override
    public Phone getPhone() {
        return new ApplePhone();
    }
}
    MiPhoneFactory、ApplePhoneFactory是生产他们自己固定手机品牌的手机,体现出专业,不需要切线,只需要工人掌握自己生产线的手机生产流程。
public class PhoneFactoryTest {
    public static void main(String[] args) {
        PhoneFactory phoneFactory = null;
        phoneFactory = new MiPhoneFactory();
        System.out.println(phoneFactory.getPhone().getName());
        phoneFactory = new ApplePhoneFactory();
        System.out.println(phoneFactory.getPhone().getName());
    }
}
 
 
小米手机
苹果手机
Process finished with exit code 0
    我们发现工厂方法比简单工厂多了一层抽象,以前我们需要什么手机,直接告诉工厂就可以了,但是现在我们需要什么样的手机必须知道生产该手机的流水线,一条流水线只能生产一种手机。这样也带来了一个问题,就是用户在需要手机时,他必须知道是什么样的流水线,并且每多生产一种手机就需要多加一条流水线。 即我们java在使用工厂方法时,必须配置好对应的工厂类,并且该工厂类只对应一个产品类
  • 抽象工厂(Abstract Factory)
public abstract class AbstractPhoneFactory {

    public abstract Phone getMiPhone();

    public abstract Phone getApplePhone();
}
public class Factory extends AbstractPhoneFactory {
    @Override
    public Phone getMiPhone() {
        return new MiPhoneFactory().getPhone();
    }

    @Override
    public Phone getApplePhone() {
        return new ApplePhoneFactory().getPhone();
    }
}
public class AbstractPhoneFactoryTest {
    public static void main(String[] args) {
        Factory factory = new Factory();
        System.out.println(factory.getApplePhone().getName());
        System.out.println(factory.getMiPhone().getName());
    }
}
 
 
苹果手机
小米手机
Process finished with exit code 0
    从抽象工厂我们可以看出,我们在工厂方法的基础上又抽象出一个抽象类,那么问题来了,我们为什么不抽象成接口呢?大家可以留言,说出自己的看法。其实在这个抽象类中就定义了我们工厂基本的一个功能,可以生产哪些手机,然后通过一个具体工厂来继承这个抽象类,用工厂方法来去实现其中定义好的功能。 这样做的好处,用户就可以很明显的从工厂类中知道该工厂的功能,并且该工厂可以创建多个具体的产品类。
    那么,大家都知道在我们框架的哪些地方用到了该抽象工厂模式?大家也可以留言说说自己看过的源码,并看看别人看过的源码是不是用到了该模式。



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值