Abstract Factory Design Pattern in Java

40 阅读3分钟

Abstract Factory

抽象工厂和工厂模式思想其实是一样的,都是把获取产品子类的逻辑抽取,根据输入条件,返回产品子类,只不过工厂模式只有一个Factory类,该类根据提供的输入条件采用if elseswatch判断返回不同的子类。

在抽象工厂模式中,实例化子类的代码不再放到 if else 语句中,而是抽取到每个子类对应的工厂类中,它们都继承抽象工厂类。 抽象工厂类定义抽象方法,返回类型是产品父类,所有子类的工厂类继承该抽象类并实现抽象方法,返回具体的产品子类。

最后定义使用者类,它为客户端类提供创建子类的入口点,里边定义获取具体子类的方法,方法的参数为抽象工厂类,然后客户端调用时根据需要,传入继承该类的子类的工厂类,在里边调用抽象方法,获取具体子类。

image.png

Abstract Factory Design Pattern Super Class and Subclasses

Computer.java

public abstract class Computer {

    public abstract String getRAM();
    public abstract String getHDD();
    public abstract String getCPU();

    @Override
    public String toString() {
        return "RAM= " + this.getRAM() + ", HDD=" + this.getHDD() + ", CPU=" + this.getCPU();
    }
}

PC.java

public class PC extends Computer {

    private String ram;
    private String hdd;
    private String cpu;

    public PC(String ram, String hdd, String cpu) {
        this.ram = ram;
        this.hdd = hdd;
        this.cpu = cpu;
    }

    public String getRAM() {
        return this.ram;
    }

    public String getHDD() {
        return this.hdd;
    }

    public String getCPU() {
        return this.cpu;
    }
}

Server.java

public class Server extends Computer {

    private String ram;
    private String hdd;
    private String cpu;

    public Server(String ram, String hdd, String cpu) {
        this.ram = ram;
        this.hdd = hdd;
        this.cpu = cpu;
    }

    public String getRAM() {
        return this.ram;
    }

    public String getHDD() {
        return this.hdd;
    }

    public String getCPU() {
        return this.cpu;
    }
}

Factory Class for Each subclass

首先,我们需要创建一个抽象工厂接口或抽象类 ComputerAbstractFactory.java

public interface ComputerAbstractFactory {
    Computer createComputer();
}

createComputer()方法正在返回一个父类Computer的实例。现在,我们的工厂类将实现这个接口,并返回它们各自的子类。

PCFactory.java

public class PCFactory implements ComputerAbstractFactory {

    private String ram;
    private String hdd;
    private String cpu;

    public PCFactory(String ram, String hdd, String cpu) {
        this.ram = ram;
        this.hdd = hdd;
        this.cpu = cpu;
    }

    public Computer createComputer() {
        return new PC(ram, hdd, cpu);
    }
}

类似地,我们将为Server子类提供一个工厂类:ServerFactory.java

public class ServerFactory implements ComputerAbstractFactory {

    private String ram;
    private String hdd;
    private String cpu;

    public ServerFactory(String ram, String hdd, String cpu) {
        this.ram = ram;
        this.hdd = hdd;
        this.cpu = cpu;
    }

    public Computer createComputer() {
        return new Server(ram, hdd, cpu);
    }
}

现在,我们将创建一个使用者类,它将为客户端类提供创建子类的入口点。ComputerFactory.java

public class ComputerFactory {
    public static Computer getComputer(ComputerAbstractFactory abstractFactory) {
        return abstractFactory.createComputer();
    }
}

注意,它是一个简单的 classgetComputer 方法,接受 ComputerAbstractFactory 参数并返回 Computer 对象。在这一点上,实现必须变得清晰起来。让我们编写一个简单的测试方法,看看如何使用抽象工厂来获取子类的实例。App.java

public class App {
    public static void main(String[] args) {
        Computer computer = ComputerFactory.getComputer(new PCFactory("2 GB","500 GB","2.4 GHz"));
        System.out.println(computer);
    }
}

总结

抽象工厂模式是健壮的,避免了工厂模式的条件逻辑。抽象工厂模式是“工厂的工厂”,可以很容易地扩展以适应更多的产品,例如,我们可以添加另一个子类笔记本电脑和一个工厂笔记本电脑工厂。