设计模式——工厂模式

工厂模式

  • 1. 引言
  • 2. 什么是工厂模式?
  • 3. 简单工厂模式
    • 汽车制造示例代码:
  • 4. 工厂方法模式
  • 5. 抽象工厂模式
  • 6. 工厂模式的优势
  • 7. 工厂模式的应用场景
  • 8. 实际应用示例:数据库连接工厂
  • 9. 结论

1. 引言

在软件开发中,创建对象是一个常见但有时复杂的任务。工厂模式作为一种创建型设计模式,提供了一种优雅的方式来处理对象的创建。

2. 什么是工厂模式?

工厂模式是一种创建型设计模式,它提供了一种创建对象的最佳方式。在工厂模式中,在创建对象时不会对客户端暴露创建逻辑,而是通过使用一个共同的接口来指向新创建的对象。

3. 简单工厂模式

汽车制造示例代码:

// 汽车接口
interface Car {
    void drive();
}
// 轿车
class Sedan implements Car {
    @Override
    public void drive() {
        System.out.println("驾驶轿车");
    }
}
// SUV
class SUV implements Car {
    @Override
    public void drive() {
        System.out.println("驾驶SUV");
    }
}
// 跑车
class SportsCar implements Car {
    @Override
    public void drive() {
        System.out.println("驾驶跑车");
    }
}
// 简单汽车工厂
class SimpleCarFactory {
    public Car createCar(String type) {
        switch (type.toLowerCase()) {
            case "sedan":
                return new Sedan();
            case "suv":
                return new SUV();
            case "sportscar":
                return new SportsCar();
            default:
                throw new IllegalArgumentException("未知的汽车类型: " + type);
        }
    }
}
// 汽车经销商
class CarDealer {
    private SimpleCarFactory factory;

    public CarDealer(SimpleCarFactory factory) {
        this.factory = factory;
    }

    public Car orderCar(String type) {
        Car car = factory.createCar(type);
        System.out.println("订购了一辆" + type);
        return car;
    }
}
// 客户端代码
public class CarExample {
    public static void main(String[] args) {
        SimpleCarFactory factory = new SimpleCarFactory();
        CarDealer dealer = new CarDealer(factory);

        Car sedan = dealer.orderCar("sedan");
        sedan.drive();

        Car suv = dealer.orderCar("suv");
        suv.drive();

        Car sportsCar = dealer.orderCar("sportscar");
        sportsCar.drive();
    }
}

在这个简单工厂模式中,SimpleCarFactory 负责创建不同类型的汽车,而 CarDealer 使用这个工厂来获取汽车实例。
简单工厂模式虽然简单,但违反了开闭原则,因为每次添加新产品都需要修改工厂类。

4. 工厂方法模式

工厂方法模式是对简单工厂模式的进一步抽象和推广。
现在,假设有不同的汽车制造商,每个制造商都有自己的生产线。

// 抽象汽车制造商
abstract class CarManufacturer {
    public Car orderCar(String type) {
        Car car = createCar(type);
        System.out.println("生产了一辆" + type);
        return car;
    }

    // 工厂方法
    protected abstract Car createCar(String type);
}
// 丰田制造商
class ToyotaManufacturer extends CarManufacturer {
    @Override
    protected Car createCar(String type) {
        switch (type.toLowerCase()) {
            case "sedan":
                return new ToyotaSedan();
            case "suv":
                return new ToyotaSUV();
            default:
                throw new IllegalArgumentException("丰田不生产这种类型的汽车: " + type);
        }
    }
}
// 特斯拉制造商
class TeslaManufacturer extends CarManufacturer {
    @Override
    protected Car createCar(String type) {
        switch (type.toLowerCase()) {
            case "sedan":
                return new TeslaSedan();
            case "suv":
                return new TeslaSUV();
            default:
                throw new IllegalArgumentException("特斯拉不生产这种类型的汽车: " + type);
        }
    }
}
// 丰田轿车
class ToyotaSedan implements Car {
    @Override
    public void drive() {
        System.out.println("驾驶丰田轿车");
    }
}
// 丰田SUV
class ToyotaSUV implements Car {
    @Override
    public void drive() {
        System.out.println("驾驶丰田SUV");
    }
}
// 特斯拉轿车
class TeslaSedan implements Car {
    @Override
    public void drive() {
        System.out.println("驾驶特斯拉轿车");
    }
}
// 特斯拉SUV
class TeslaSUV implements Car {
    @Override
    public void drive() {
        System.out.println("驾驶特斯拉SUV");
    }
}
// 客户端代码
public class CarExample {
    public static void main(String[] args) {
        CarManufacturer toyota = new ToyotaManufacturer();
        CarManufacturer tesla = new TeslaManufacturer();

        Car toyotaSedan = toyota.orderCar("sedan");
        toyotaSedan.drive();

        Car teslaSUV = tesla.orderCar("suv");
        teslaSUV.drive();
    }
}

在这个工厂方法模式中,每个具体的汽车制造商都实现了自己的 createCar 方法,允许不同的制造商创建自己品牌的汽车。
这些例子展示了工厂模式如何将对象的创建与使用分离,提供了一种灵活的方式来创建不同类型的对象:

  1. 简单工厂模式适用于创建对象的逻辑相对简单的情况,如一个通用的汽车工厂。
  2. 工厂方法模式则更适合需要不同变体的情况,如不同品牌的汽车制造商。

工厂方法模式符合开闭原则,允许系统在不修改现有代码的情况下引入新的产品类型。

5. 抽象工厂模式

抽象工厂模式提供一个创建一系列相关或相互依赖对象的接口,而无需指定它们具体的类。
在这个例子中,将考虑不同类型的汽车部件(如引擎、轮胎)以及不同的汽车制造商。每个制造商都会生产这些部件的特定版本。

// 抽象产品 - 引擎
interface Engine {
    void start();
}
// 抽象产品 - 轮胎
interface Tire {
    void rotate();
}
// 具体产品 - 丰田引擎
class ToyotaEngine implements Engine {
    @Override
    public void start() {
        System.out.println("丰田引擎启动");
    }
}
// 具体产品 - 丰田轮胎
class ToyotaTire implements Tire {
    @Override
    public void rotate() {
        System.out.println("丰田轮胎旋转");
    }
}
// 具体产品 - 特斯拉引擎
class TeslaEngine implements Engine {
    @Override
    public void start() {
        System.out.println("特斯拉电动引擎启动");
    }
}
// 具体产品 - 特斯拉轮胎
class TeslaTire implements Tire {
    @Override
    public void rotate() {
        System.out.println("特斯拉轮胎旋转");
    }
}
// 抽象工厂
interface CarFactory {
    Engine createEngine();
    Tire createTire();
}
// 具体工厂 - 丰田工厂
class ToyotaFactory implements CarFactory {
    @Override
    public Engine createEngine() {
        return new ToyotaEngine();
    }

    @Override
    public Tire createTire() {
        return new ToyotaTire();
    }
}
// 具体工厂 - 特斯拉工厂
class TeslaFactory implements CarFactory {
    @Override
    public Engine createEngine() {
        return new TeslaEngine();
    }

    @Override
    public Tire createTire() {
        return new TeslaTire();
    }
}
// 汽车类
class Car {
    private Engine engine;
    private Tire tire;

    public Car(CarFactory factory) {
        engine = factory.createEngine();
        tire = factory.createTire();
    }

    public void start() {
        engine.start();
        tire.rotate();
    }
}
// 客户端代码
public class AbstractFactoryExample {
    public static void main(String[] args) {
        // 创建丰田汽车
        CarFactory toyotaFactory = new ToyotaFactory();
        Car toyotaCar = new Car(toyotaFactory);
        System.out.println("启动丰田汽车:");
        toyotaCar.start();

        System.out.println();

        // 创建特斯拉汽车
        CarFactory teslaFactory = new TeslaFactory();
        Car teslaCar = new Car(teslaFactory);
        System.out.println("启动特斯拉汽车:");
        teslaCar.start();
    }
}

在这个抽象工厂模式的例子中:

  1. 定义了两个抽象产品接口: Engine 和 Tire。
  2. 对于每个制造商(丰田和特斯拉),创建了这些接口的具体实现。
  3. CarFactory 是抽象工厂接口,声明了创建引擎和轮胎的方法。
  4. ToyotaFactory 和 TeslaFactory 是具体的工厂,实现了 CarFactory 接口,负责创建各自品牌的引擎和轮胎。
  5. Car 类使用给定的工厂来创建它的部件(引擎和轮胎)。
  6. 在客户端代码中,可以使用不同的工厂来创建不同品牌的汽车,而无需关心具体的部件创建过程。

抽象工厂模式的优点:

  1. 它确保一个族的产品对象相互匹配。例如,丰田引擎总是与丰田轮胎配对,特斯拉引擎总是与特斯拉轮胎配对。
  2. 它将具体类的创建封装在具体工厂中,使客户端与具体类解耦。
  3. 添加新的产品族很容易。例如,如果想添加一个新的汽车制造商(如宝马),只需创建新的具体产品类和一个新的具体工厂类。
  4. 它促进了产品的一致性。当产品对象需要一起工作时,抽象工厂确保一个应用始终只使用同一个族的对象。

6. 工厂模式的优势

  • 封装性好,创建对象的细节对客户端透明。
  • 符合单一职责原则,将创建对象的职责从使用对象的代码中分离出来。
  • 可扩展性强,遵循开闭原则。

7. 工厂模式的应用场景

  • 当一个类不知道它所必须创建的对象的类时。
  • 当一个类希望由它的子类来指定它所创建的对象时。
  • 当类将创建对象的职责委托给多个帮助子类中的某一个,并且你希望将哪一个帮助子类是代理者这一信息局部化时。

8. 实际应用示例:数据库连接工厂

interface DatabaseConnection {
    void connect();
    void disconnect();
}

class MySQLConnection implements DatabaseConnection {
    @Override
    public void connect() {
        System.out.println("Connecting to MySQL database");
    }

    @Override
    public void disconnect() {
        System.out.println("Disconnecting from MySQL database");
    }
}

class PostgreSQLConnection implements DatabaseConnection {
    @Override
    public void connect() {
        System.out.println("Connecting to PostgreSQL database");
    }

    @Override
    public void disconnect() {
        System.out.println("Disconnecting from PostgreSQL database");
    }
}

interface DatabaseConnectionFactory {
    DatabaseConnection createConnection();
}

class MySQLConnectionFactory implements DatabaseConnectionFactory {
    @Override
    public DatabaseConnection createConnection() {
        return new MySQLConnection();
    }
}

class PostgreSQLConnectionFactory implements DatabaseConnectionFactory {
    @Override
    public DatabaseConnection createConnection() {
        return new PostgreSQLConnection();
    }
}

public class DatabaseClient {
    public static void main(String[] args) {
        DatabaseConnectionFactory mysqlFactory = new MySQLConnectionFactory();
        DatabaseConnection mysqlConnection = mysqlFactory.createConnection();
        mysqlConnection.connect();
        mysqlConnection.disconnect();

        DatabaseConnectionFactory postgresFactory = new PostgreSQLConnectionFactory();
        DatabaseConnection postgresConnection = postgresFactory.createConnection();
        postgresConnection.connect();
        postgresConnection.disconnect();
    }
}

这个例子展示了如何使用工厂模式来创建不同类型的数据库连接,而不需要在客户端代码中直接实例化具体的连接类。

9. 结论

工厂模式是一种强大而灵活的创建型设计模式,它可以帮助解耦对象的创建和使用。从简单工厂到抽象工厂,每种形式都有其适用的场景。通过掌握工厂模式,可以编写出更加灵活、可维护和可扩展的代码。

你可能感兴趣的:(设计模式,设计模式,python,开发语言)