Java设计模式系列(2):工厂模式

布鸽不鸽 Lv4

前言

正常情况下,我们如果有PhoneStore类,其中需要有orderPhone(String type)方法,为用户提供不同的Phone。此时代码耦合十分严重,如果我们要更换或增加对象,都需要改new对象的地方。我们其实可以使用工厂类来生成对象,PhoneStore只需要和工厂打交道即可,实现最终目的:解耦

原文地址:https://xuedongyun.cn/post/33663/

简单工厂模式

简单工厂包含:

  • 抽象产品(Phone
  • 具体产品(XiaomiPhoneHuaweiPhone
  • 具体工厂(PhoneFactory
1
2
3
4
5
6
7
8
9
10
11
12
13
public class PhoneFactory {

// 这里方法也可以设置为static,即“静态工厂模式”
public Phone createPhone(String type) {
Phone phone = null;
if (type.equals("xiaomi")) {
phone = new XiaomiPhone();
} else if (type.equals("huawei")) {
phone = new HuaweiPhone();
}
return phone;
}
}

此时,PhoneStore需要手机时,只需要从PhoneFactory中获取即可

问题:要增加新的手机,就需要修改PhoneFactory的代码,违背开闭原则

工厂方法模式

工厂方法模式包含:

  • 抽象产品(Phone
  • 具体产品(XiaomiPhoneHuaweiPhone
  • 抽象工厂(PhoneFactory
  • 具体工厂(XiaomiPhoneFactoryHuaweiPhoneFactory

抽象工厂

1
2
3
4
public interface PhoneFactory {

Phone createPhone();
}

具体工厂

1
2
3
4
5
6
public class XiaomiPhoneFactory implement PhoneFactory {

public Phone createPhone() {
return new XiaomiPhoneFactory();
}
}

PhoneStore中具体使用

1
2
3
4
5
6
7
8
9
10
11
12
13
public class PhoneStore {

private PhoneFactory factory;

public PhoneStore(PhoneFactory factory) {
this.factory = factory;
}

public Phone orderPhone() {
Phone phone = factory.createPhone();
return phone;
}
}

此时,当增加手机时,无需修改PhoneFactory,只需要增加新的接口实现类即可

问题:每增加一种手机,就要创建一个新的对应工厂类,增加了系统复杂度

抽象工厂模式

image-20200401214509176
  • 工厂方法模式:只能生产一个级别的产品

  • 抽象工厂模式:生产多个级别的产品

现在工厂可以生产同一产品族的产品,比如手机和电脑。小米和华为都会生产自己的手机和电脑。现在关系如图:

classDiagram

class XiaomiFactory {
    + createPhone(): Phone
    + createComputer(): Computer
}

class HuaweiFactory {
    + createPhone(): Phone
    + createComputer(): Computer
}
    
Phone <|-- XiaomiPhone
Phone <|-- HuaweiPhone

Computer <|-- XiaomiComputer
Computer <|-- HuaweiComputer

XiaomiPhone <.. XiaomiFactory
XiaomiComputer <.. XiaomiFactory

HuaweiPhone <.. HuaweiFactory
HuaweiComputer <.. HuaweiFactory

XiaomiFactory ..|> DeviceFacotry
HuaweiFactory ..|> DeviceFacotry

抽象工厂

1
2
3
4
5
6
public interface DeviceFactory {

Phone createPhone();

Computer createComputer();
}

具体工厂

1
2
3
4
5
6
7
8
9
10
public class xiaomiFactory implement DeviceFactory {

public Phone createPhone() {
return new XiaomiPhone();
}

public Computer createComputer() {
return new XiaomiComputer();
}
}

现在,当一个产品族种的多个对象被设计成一起工作时,能保证客户端只使用同一个产品族种的对象

问题:产品族中需要增加新的产品时,所有工厂类都需要修改

JDK源码-Collection.iterator方法

1
2
3
4
5
6
7
8
9
10
ArrayList<Integer> list = new ArrayList<>();
list.add(1);
list.add(2);
list.add(3);

Iterator<Integer> it = list.iterator();

while (it.hasNext()) {
System.out.println("it.next() = " + it.next());
}

获取迭代器时,使用了工厂方法模式,类图如下

classDiagram
class Iterator {
    <>
}
class Collection {
    <>
    + iterator(): Iterator
}
class ArrayList {
    + iterator(): Iterator
}

Collection <|.. ArrayList
Iterator <|.. ArrayList_Itr
Iterator <.. Collection
ArrayList_Itr <.. ArrayList

Factory <|.. EntityFactory
Product <|.. EntityProduct
Product <.. Factory
EntityProduct <.. EntityFactory

抽象产品:Iterator

具体产品:ArrayList.Itr

抽象工厂:Collection

具体工厂:ArrayList

  • 标题: Java设计模式系列(2):工厂模式
  • 作者: 布鸽不鸽
  • 创建于 : 2023-06-21 17:14:38
  • 更新于 : 2023-06-23 22:02:40
  • 链接: https://xuedongyun.cn//post/33663/
  • 版权声明: 本文章采用 CC BY-NC-SA 4.0 进行许可。
评论