工厂模式-创建型

前言

工厂模式的核心思想是将对象的创建隐藏到工厂内部,而不是暴露在代码调用处

一、简单工厂模式

1.1、属于创建型模式

绕开new,避免对象创建过程中所导致的紧耦合(依赖具体类),从而支持对象创建的稳定。

为什么使用创建型模式?

在软件系统种,由于需求的变化,需要创建的对象的具体类型变化经常变化。

1.2、说明

简单工厂模式,并不在GoF的23中设计模式当中,但它确实工厂模式的一个基础。

1.3、核心思想

定义一个工厂类,根据传入的参数不同,返回不同的产品实例。<========>通过参数告诉需求,然后根据需求返回不同的实例,不过多关注实例的实现。

1.4、为什么要用简单工厂模式

经典问题场景:

拥有一个图形绘制程序,需要创建不同形状:

cpp 复制代码
// 糟糕的实现:客户端需要知道所有具体类
class Circle {
public:
    void draw() { cout << "绘制圆形" << endl; }
};

class Rectangle {
public:
    void draw() { cout << "绘制矩形" << endl; }
};

class Triangle {
public:
    void draw() { cout << "绘制三角形" << endl; }
};

// 客户端代码
void drawShape(const string& type) {
    if (type == "circle") {
        Circle shape;
        shape.draw();
    } else if (type == "rectangle") {
        Rectangle shape;
        shape.draw();
    } else if (type == "triangle") {
        Triangle shape;
        shape.draw();
    }
    // 每增加一个形状,就要修改这里的if-else!
}

问题点:

  1. 客户端与具体类紧密耦合
  2. 违反 开闭原则,如果要增加新的形状类,就需要修改客户端代码

使用简单工厂模式之后

  1. 定义产品接口
cpp 复制代码
// 抽象产品类
class Shape {
public:
    virtual ~Shape() = default;
    virtual void draw() const = 0;
    virtual string getName() const = 0;
};
  1. 定义具体产品类
cpp 复制代码
// 具体产品类
class Circle : public Shape {
public:
    void draw() const override {
        cout << "绘制圆形" << endl;
    }
    
    string getName() const override {
        return "圆形";
    }
};

class Rectangle : public Shape {
public:
    void draw() const override {
        cout << "绘制矩形" << endl;
    }
    
    string getName() const override {
        return "矩形";
    }
};

class Triangle : public Shape {
public:
    void draw() const override {
        cout << "绘制三角形" << endl;
    }
    
    string getName() const override {
        return "三角形";
    }
};
  1. 创建工厂类(核心点)
cpp 复制代码
// 简单工厂类
class ShapeFactory {
public:
    // 静态工厂方法,根据类型字符串创建对象
    static unique_ptr<Shape> createShape(const string& type) {
        if (type == "circle") {
            return make_unique<Circle>();
        } else if (type == "rectangle") {
            return make_unique<Rectangle>();
        } else if (type == "triangle") {
            return make_unique<Triangle>();
        } else {
            throw invalid_argument("未知的形状类型: " + type);
        }
    }
    
    // 也可以使用枚举来避免字符串硬编码
    enum class ShapeType { CIRCLE, RECTANGLE, TRIANGLE };
    
    static unique_ptr<Shape> createShape(ShapeType type) {
        switch (type) {
            case ShapeType::CIRCLE:
                return make_unique<Circle>();
            case ShapeType::RECTANGLE:
                return make_unique<Rectangle>();
            case ShapeType::TRIANGLE:
                return make_unique<Triangle>();
            default:
                throw invalid_argument("未知的形状类型");
        }
    }
};
  1. 客户端代码
cpp 复制代码
// 客户端代码 - 变得非常简洁!
void demo() {
    cout << "=== 简单工厂模式演示 ===" << endl;
    
    try {
        // 使用字符串创建
        auto circle = ShapeFactory::createShape("circle");
        auto rectangle = ShapeFactory::createShape("rectangle");
        auto triangle = ShapeFactory::createShape("triangle");
        
        circle->draw();
        rectangle->draw();
        triangle->draw();
        
        cout << "------------------------" << endl;
        
        // 使用枚举创建(更安全)
        auto circle2 = ShapeFactory::createShape(ShapeFactory::ShapeType::CIRCLE);
        auto rect2 = ShapeFactory::createShape(ShapeFactory::ShapeType::RECTANGLE);
        
        cout << "形状: " << circle2->getName() << endl;
        circle2->draw();
        
    } catch (const exception& e) {
        cout << "错误: " << e.what() << endl;
    }
}

附上UML类图

1.4、优缺点

优点 缺点
客户端与具体类解耦 违反开闭原则,每新增一个产品就需要修改工厂类
集中化对象创建 工厂类职责过重,所有创建逻辑集中在一个类中
便于统一管理 产品较多时代码会显得臃肿
隐藏创建细节 不易于扩展

1.5、适用场景

  • 支付系统(支付宝,微信,现金,银行卡等支付方式)
  • 数据库连接(MySql,SQLite,Oracle等)
  • 日志系统(创建文件日志,控制台日志,数据库日志等)

如果只有2~3种产品,直接new会更简单,不要为了用而用,从而过度设计

1.5、简单工厂的变种:

利用注册

cpp 复制代码
// 使用注册表避免if-else链
class ShapeFactory {
private:
    using Creator = std::function<std::unique_ptr<Shape>()>;
    static std::unordered_map<std::string, Creator> registry;
    
public:
    static void registerShape(const std::string& type, Creator creator) {
        registry[type] = creator;
    }
    
    static std::unique_ptr<Shape> createShape(const std::string& type) {
        auto it = registry.find(type);
        if (it != registry.end()) {
            return it->second();
        }
        throw std::invalid_argument("未知类型: " + type);
    }
};

// 注册具体产品
class ShapeRegistrar {
public:
    ShapeRegistrar(const std::string& type) {
        ShapeFactory::registerShape(type, []() { 
            return std::make_unique<Circle>(); 
        });
    }
};

// 自动注册
static ShapeRegistrar circleRegistrar("circle");

二、工厂方法模式

2.1、核心思想

定义一个用于创建对象的接口,但让子类决定实例化哪一个类。工厂方法使一个类的实例化延迟到其子类。

2.2、与简单工厂的关键区别

简单工厂把创建逻辑集中在一个类中,而工厂方法模式将创建逻辑分散到各个子类中。

2.3、代码展示

  1. 定义抽象产品类
cpp 复制代码
// 抽象产品
class Document {
public:
    virtual ~Document() = default;
    virtual void open() = 0;
    virtual void save() = 0;
    virtual std::string getType() const = 0;
};
  1. 定义具体产品类
cpp 复制代码
// 具体产品
class WordDocument : public Document {
public:
    void open() override {
        std::cout << "打开Word文档,显示文字处理界面" << std::endl;
    }
    
    void save() override {
        std::cout << "保存为.docx格式" << std::endl;
    }
    
    std::string getType() const override {
        return "Word文档";
    }
};

class ExcelDocument : public Document {
public:
    void open() override {
        std::cout << "打开Excel文档,显示表格界面" << std::endl;
    }
    
    void save() override {
        std::cout << "保存为.xlsx格式" << std::endl;
    }
    
    std::string getType() const override {
        return "Excel文档";
    }
};

class PdfDocument : public Document {
public:
    void open() override {
        std::cout << "打开PDF文档,显示只读内容" << std::endl;
    }
    
    void save() override {
        std::cout << "PDF文档不支持编辑保存" << std::endl;
    }
    
    std::string getType() const override {
        return "PDF文档";
    }
};
  1. 定义工厂类
cpp 复制代码
class Application {
public:
    virtual ~Application() = default;
    
    // 工厂方法 - 由子类实现
    virtual std::unique_ptr<Document> createDocument() = 0;
    
    // 业务方法
    void newDocument() {
        std::cout << "创建新文档..." << std::endl;
        auto doc = createDocument();  // 调用工厂方法
        doc->open();
        documents_.push_back(std::move(doc));
    }
    
    void listDocuments() {
        std::cout << "当前打开的文档:" << std::endl;
        for (const auto& doc : documents_) {
            std::cout << " - " << doc->getType() << std::endl;
        }
    }

private:
    std::vector<std::unique_ptr<Document>> documents_;
};
  1. 定义具体创建子类
cpp 复制代码
// 具体创建者
class WordApplication : public Application {
public:
    std::unique_ptr<Document> createDocument() override {
        return std::make_unique<WordDocument>();
    }
};

class ExcelApplication : public Application {
public:
    std::unique_ptr<Document> createDocument() override {
        return std::make_unique<ExcelDocument>();
    }
};

class PdfApplication : public Application {
public:
    std::unique_ptr<Document> createDocument() override {
        return std::make_unique<PdfDocument>();
    }
};
  1. 客户端代码
cpp 复制代码
void demoFactoryMethod() {
    std::cout << "=== 工厂方法模式演示 ===" << std::endl;
    
    auto wordApp = std::make_unique<WordApplication>();
    wordApp->newDocument();  // 创建Word文档
    wordApp->listDocuments();
    
    std::cout << "------------------------" << std::endl;
    
    auto excelApp = std::make_unique<ExcelApplication>();
    excelApp->newDocument();  // 创建Excel文档
    excelApp->listDocuments();
}

2.4、补充

cpp 复制代码
// 模板工厂方法 - 编译期多态
template<typename Product>
class GenericCreator {
public:
    static std::unique_ptr<Product> create() {
        return std::make_unique<Product>();
    }
};

// 使用
auto doc = GenericCreator<WordDocument>::create();

附上UML类图

三、抽象工厂模式

3.1、核心思想

提供一个接口,用于创建相关或依赖对象的家族,而不需要明确指定具体类。

***注意:***创建的是产品家族,而不是单个产品

3.2、代码展示

  1. 定义抽象产品类
cpp 复制代码
// 抽象产品 - UI组件
class Button {
public:
    virtual ~Button() = default;
    virtual void render() const = 0;
};

class TextField {
public:
    virtual ~TextField() = default;
    virtual void render() const = 0;
};

class CheckBox {
public:
    virtual ~CheckBox() = default;
    virtual void render() const = 0;
};
  1. 定义具体产品类
cpp 复制代码
// 具体产品
class WinButton : public Button {
public:
    void render() const override {
        std::cout << "渲染Windows风格的按钮" << std::endl;
    }
};

class MacButton : public Button {
public:
    void render() const override {
        std::cout << "渲染MacOS风格的按钮" << std::endl;
    }
};

class WinTextField : public TextField {
public:
    void render() const override {
        std::cout << "渲染Windows风格文本框" << std::endl;
    }
};
  1. 定义抽象工厂类
cpp 复制代码
class GUIFactory {
public:
    virtual ~GUIFactory() = default;
    virtual std::unique_ptr<Button> createButton() = 0;
    virtual std::unique_ptr<TextField> createTextField() = 0;
    virtual std::unique_ptr<CheckBox> createCheckBox() = 0;
};
  1. 定义具体工厂类
cpp 复制代码
class WinFactory : public GUIFactory {
public:
    std::unique_ptr<Button> createButton() override {
        return std::make_unique<WinButton>();
    }
    std::unique_ptr<TextField> createTextField() override {
        return std::make_unique<WinTextField>();
    }
    std::unique_ptr<CheckBox> createCheckBox() override {
        return std::make_unique<WinCheckBox>();
    }
};

class MacFactory : public GUIFactory {
public:
    std::unique_ptr<Button> createButton() override {
        return std::make_unique<MacButton>();
    }
    std::unique_ptr<TextField> createTextField() override {
        return std::make_unique<MacTextField>();
    }
    std::unique_ptr<CheckBox> createCheckBox() override {
        return std::make_unique<MacCheckBox>();
    }
};
  1. 客户端代码
cpp 复制代码
class ApplicationUI {
private:
    std::unique_ptr<GUIFactory> factory_;
    
public:
    ApplicationUI(std::unique_ptr<GUIFactory> factory) 
        : factory_(std::move(factory)) {}
    
    void createUI() {
        std::cout << "\n=== 创建应用界面 ===" << std::endl;
        
        auto button = factory_->createButton();
        auto checkbox = factory_->createCheckbox();
        auto textbox = factory_->createTextBox();
        
        button->render();
        button->onClick();
        
        checkbox->render();
        checkbox->onCheck();
        
        textbox->render();
        textbox->onInput();
    }
};

// 使用示例
void demoAbstractFactory() {
    std::cout << "=== 抽象工厂模式演示 ===" << std::endl;
    
    // Windows风格界面
    auto windowsUI = ApplicationUI(std::make_unique<WindowsFactory>());
    windowsUI.createUI();
    
    // macOS风格界面
    auto macUI = ApplicationUI(std::make_unique<MacFactory>());
    macUI.createUI();
    
    // Linux风格界面
    auto linuxUI = ApplicationUI(std::make_unique<LinuxFactory>());
    linuxUI.createUI();
}

3.3、补充

cpp 复制代码
// 使用variant返回不同类型产品
class ModernGUIFactory {
public:
    using ButtonVariant = std::variant<WinButton, MacButton, LinuxButton>;
    
    virtual ButtonVariant createButton() = 0;
    virtual auto createTextField() = 0;  // 自动推导返回类型
};

四、实战

以魔兽世界为例:游戏中存在多种角色(战士,法师,武僧,术士,猎人等);利用工厂模式实现角色创建系统。

cpp 复制代码
// 定义角色的基本属性
class Character
{
    protected:
        std::string name;           // 角色名称
        int health;                 // 生命值
        int attack;                 // 攻击力
        int defense;                // 防御力
        int magic;                  // 魔法值
    
    public:
        Character(const std::string& name, int health, int attack, int defense, int magic)
        : name(name), health(health), attack(attack), defense(defense), magic(magic) {}

        virtual ~Character() = default;

        virtual void PrintInfo() const
        {
            std::cout << "角色名称: " << name
                      << ", 生命值: " << health
                      << ", 攻击力: " << attack
                      << ", 防御力: " << defense
                      << ", 魔法值: " << magic << std::endl;
        }

        virtual void SpecialSkill() = 0;

        std::string GetName() const { return name; }
};

// 定义具体角色
// 战士
class Warrior : public Character
{
public:
    Warrior(const std::string& name)
        : Character(name, 150, 80, 80, 20) {
    }

    void SpecialSkill() override
    {
        std::cout << "战士技能:冲锋" << std::endl;
    }

    void PrintInfo() const override;
    {
        std::cout << "战士名称: " << name << std::endl;
        Character::PrintInfo();
        std::cout << "特点:近战攻击,攻击力高" << std::endl;
    }
};

// 法师
class Mage : public Character
{
public:
    Mage(const std::string& name)
        : Character(name, 80, 30, 40, 120) {
    }

    void SpecialSkill() override
    {
        std::cout << "法师技能:火球术" << std::endl;
    }

    void PrintInfo() const override
    {
        std::cout << "法师名称: " << name << std::endl;
        Character::PrintInfo();
        std::cout << "特点:魔法攻击,高魔法值" << std::endl;
    }
};

// 武僧
class Monk : public Character
{
public:
    Monk(const std::string& name)
        : Character(name, 100, 80, 80, 80) {
    }

    void SpecialSkill() override
    {
        std::cout << "武僧技能:禅意拳" << std::endl;
    }

    void PrintInfo() const override
    {
        std::cout << "武僧名称: " << name << std::endl;
        Character::PrintInfo();
        std::cout << "特点:近战高攻防,平衡属性" << std::endl;
    }
};

简单工厂

cpp 复制代码
// 枚举每一种角色
enum class CharacterType
{
    Warrior, Mage, Monk
};

// 简单工厂类,根据类型创建角色
class SimpleCharacterFactory
{
    public:
        // 静态工厂方法,根据类型创建角色实例
        static std::unique_ptr<Character> Create(const std::string& name, CharacterType type)
        {
            switch (type)
            {
                case CharacterType::Warrior: return std::make_unique<Warrior>(name);
                case CharacterType::Mage: return std::make_unique<Mage>(name);
                case CharacterType::Monk: return std::make_unique<Monk>(name);
                default: throw std::invalid_argument("Invalid character type");
            }
        }
};

显而易见,如果未来新增角色,比如术士,牧师等,要添加相应的类,枚举,以及新的case;会比较麻烦并且违背了开闭原则。

工厂方法模式

cpp 复制代码
// 抽象工厂接口
class CharacterFactory
{
    public:
        virtual ~CharacterFactory() = default;
        virtual std::unique_ptr<Character> CreateCharacter(const std::string& name) const = 0;

        // 真正的接口:创建角色并进行初始化
        std::unique_ptr<Character> CreateCharacterWithSetup(const std::string& name)
        {
            // 利用继承和多态的特性,在创建角色后进行初始化操作
            auto character = CreateCharacter(name);
            SetupCharacter(character.get());
            return character;
        }
    protected:
        // 通用初始化流程
        virtual void SetupCharacter(Character& character)
        {
            std::cout<<"角色 "<< character.GetName() << " 已创建" << std::endl;
        }
};

// 具体工厂类,根据类型创建角色实例
class WarriorFactory : public CharacterFactory
{
    public:
        virtual std::unique_ptr<Character> CreateCharacter(const std::string& name) const override
        {
            return std::make_unique<Warrior>(name);
        }
    protected:
        virtual void SetupCharacter(Character& character) override
        {
            CharacterFactory::SetupCharacter(character);
            std::cout<<"战士 "<< character.GetName() << " 已初始化" << std::endl;       // 战士的初始化
            std::cout<<"初始装备为长剑和盾牌\n";
        }
};

class MageFactory : public CharacterFactory
{
    public:
        virtual std::unique_ptr<Character> CreateCharacter(const std::string& name) const override
        {
            return std::make_unique<Mage>(name);
        }
    protected:
        virtual void SetupCharacter(Character& character) override
        {
            CharacterFactory::SetupCharacter(character);
            std::cout<<"法师 "<< character.GetName() << " 已初始化" << std::endl;       // 法师的初始化
            std::cout<<"初始装备为法杖\n";
        }
};

class MonkFactory : public CharacterFactory
{
    public:
        virtual std::unique_ptr<Character> CreateCharacter(const std::string& name) const override
        {
            return std::make_unique<Monk>(name);
        }
    protected:
        virtual void SetupCharacter(Character& character) override
        {
            CharacterFactory::SetupCharacter(character);
            std::cout<<"武僧 "<< character.GetName() << " 已初始化" << std::endl;       // 武僧的初始化
            std::cout<<"初始装备为禅杖\n";
        }
};

当每个角色需要修改时,不会影响到其他角色。如果需要增加新的角色,只需要添加一个新的工厂类即可。

还有如果角色的创建还依赖于其他参数,比如装备,种族等,那么工厂方法会显得难以完成。这时候就需要抽象工厂,创建一系列家族产品。

抽象工厂

cpp 复制代码
// 抽象基类
class Equipment
{
    public:
        virtual ~Equipment() = default;
        virtual std::string GetDescription() const = 0;
};

// 具体装备类
class HumanSword : public Equipment
{
    public:
        std::string GetDescription() const override
        {
            return "人类专属武器-长剑";
        }
};

class HumanShield : public Equipment
{
    public:
        std::string GetDescription() const override
        {
            return "人类专属-盾牌";
        }
};

class ElfSword : public Equipment
{
    public:
        std::string GetDescription() const override
        {
            return "精灵专属武器-短剑";
        }
};

class ElfShield : public Equipment
{
public:
    std::string GetDescription() const override
    {
        return "精灵专属-魔法盾";
    }
};

class PandEquip : public Equipment
{
public:
    std::string GetDescription() const override
    {
        return "熊猫人专属武器-禅杖";
    }
};

class PandaShield : public Equipment
{
public:
    std::string GetDescription() const override
    {
        return "";
    }
};

// 抽象工厂,种族工厂
class RaceFactory
{
    public:
        virtual ~RaceFactory() = default;
        virtual std::unique_ptr<Character> CreateWarrior(const std::string& name) const = 0;
        virtual std::unique_ptr<Character> CreateMage(const std::string& name) const = 0;
        virtual std::unique_ptr<Character> CreateMonk(const std::string& name) const = 0;
        virtual std::unique_ptr<Equipment> CreateWeapon() const = 0;
        virtual std::unique_ptr<Equipment> CreateShield() const = 0;
        virtual std::string GetRaceName() const = 0;
};

// 具体种族角色类
class HumanWarrior : public Warrior
{
public:
    HumanWarrior(const std::string& name) : Warrior(name + "(人族)") {}

    void PrintInfo() const override
    {
        std::cout << "=========人类战士=========\n";

        Character::PrintInfo();
        std::cout << "特长:均衡发展,适应力量" << std::endl;
    }
};

class ElfMage : public Mage
{
public:
    ElfMage(const std::string& name) : Mage(name + "(精灵)") {}

    void PrintInfo() const override
    {
        std::cout << "=========精灵法师=========\n";

        Character::PrintInfo();
        std::cout << "特长:智力过人,魔力充足" << std::endl;
    }
};

class PandaMonk : public Monk
{
public:
    PandaMonk(const std::string& name) : Monk(name + "(熊猫人)") {}

    void PrintInfo() const override
    {
        std::cout << "=========熊猫人武僧=========\n";

        Character::PrintInfo();
        std::cout << "特长:爱好和平" << std::endl;
    }
};

// 具体工厂类
class HumanRaceFactory : public RaceFactory
{
    public:
        std::unique_ptr<Character> CreateWarrior(const std::string& name) const override
        {
            return std::make_unique<HumanWarrior>(name);
        }

        std::unique_ptr<Character> CreateMage(const std::string& name) const override
        {
            return std::make_unique<ElfMage>(name);
        }

        std::unique_ptr<Character> CreateMonk(const std::string& name) const override
        {
            return std::make_unique<PandaMonk>(name);
        }

        std::unique_ptr<Equipment> CreateWeapon() const override
        {
            return std::make_unique<HumanSword>();
        }

        std::unique_ptr<Equipment> CreateShield() const override
        {
            return std::make_unique<HumanShield>();
        }

        std::string GetRaceName() const override
        {
            return "人类";
        }
};

class ElfRaceFactory : public RaceFactory
{
public:
    std::unique_ptr<Character> CreateWarrior(const std::string& name) const override
    {
        return std::make_unique<HumanWarrior>(name);
    }

    std::unique_ptr<Character> CreateMage(const std::string& name) const override
    {
        return std::make_unique<ElfMage>(name);
    }

    std::unique_ptr<Character> CreateMonk(const std::string& name) const override
    {
        return std::make_unique<PandaMonk>(name);
    }

    std::unique_ptr<Equipment> CreateWeapon() const override
    {
        return std::make_unique<ElfSword>();
    }
    std::unique_ptr<Equipment> CreateShield() const override
    {
        return std::make_unique<ElfShield>();
    }

    std::string GetRaceName() const override
    {
        return "精灵";
    }
};

class PandaRaceFactory : public RaceFactory
{
public:
    std::unique_ptr<Character> CreateWarrior(const std::string& name) const override
    {
        return std::make_unique<HumanWarrior>(name);
    }

    std::unique_ptr<Character> CreateMage(const std::string& name) const override
    {
        return std::make_unique<ElfMage>(name);
    }

    std::unique_ptr<Character> CreateMonk(const std::string& name) const override
    {
        return std::make_unique<PandaMonk>(name);
    }

    std::unique_ptr<Equipment> CreateWeapon() const override
    {
        return std::make_unique<PandEquip>();
    }

    std::unique_ptr<Equipment> CreateShield()const override
    {
        return std::make_unique<PandaShield>();
    }

    std::string GetRaceName() const override
    {
        return "熊猫人";
    }
};

最后,使用这些工厂和角色:

cpp 复制代码
int main()
{
    std::cout<<"============简单工厂模式示例===========\n";
    auto SimpleWarrior = SimpleFactory::CreateCharacter(CharacterType::WARRIOR, "战士-小吼");
    std::cout<<"创建结果: "<< SimpleWarrior->GetName() << std::endl;

    std::cout<<"=============工厂方法==============\n";
    auto methFactory = std::make_unique<MajorFactory>();
    auto methMajor = methFactory->CreateCharacterWithSetup("法师-雅典娜");
    std::cout<<"创建结果: "<< methMajor->GetName() << std::endl;

    std::cout<<"==============抽象工厂模式==============\n";
    auto abstractFactory = std::make_unique<PandaRaceFactory>();
    auto abstractMonk = abstractFactory->CreateMonk("武僧-熊猫酒仙");
    auto abstractWeapon = abstractFactory->CreateWeapon();
    std::cout<<"创建结果: "<< abstractMonk->GetName() <<" + "<< abstractWeapon->GetDescription() << std::endl;

    return 0;
}

工厂模式的对比:

简单工厂 工厂方法 抽象工厂
核心思想 一个工厂类,根据参数创建不同产品 将创建延迟到子类,每个子类创建一种产品 创建相关产品家族,保证产品兼容性
创建目标 单一产品 单个产品系列中的具体产品 相关或依赖的产品家族
扩展性 差(增加新产品需修改工厂类) 好(新增产品只需添加子类,无需改动原有代码) 非常好(新增系列产品只需添加新工厂和对应的产品实现)
开闭原则 违背(修改工厂类) 遵循(新增子类不修改原有代码) 遵循(新增产品家族只需添加新工厂和实现,无需改动现有代码)
复杂度 中(引入了抽象层,增加了复杂性) 高(需要维护多个工厂和产品类)
适用场景 产品类型固定,变化少 产品类型可能频繁增加 需要保证产品兼容性,创建相关产品组
相关推荐
qq_310658517 小时前
mediasoup源码走读(六)——NetEQ
服务器·c++·音视频
qq_433554548 小时前
C++树形DP(树上分组背包)
c++·算法·深度优先
电子_咸鱼8 小时前
常见面试题——滑动窗口算法
c++·后端·python·算法·leetcode·哈希算法·推荐算法
肥大毛10 小时前
C++入门学习---结构体
开发语言·c++·学习
何中应10 小时前
【面试题-5】设计模式
java·开发语言·后端·设计模式·面试题
小猪猪屁10 小时前
顺序表与链表:头插法与尾插法详解
c语言·数据结构·c++
历程里程碑11 小时前
C++ 5:模板初阶
c语言·开发语言·数据结构·c++·算法
dllmayday11 小时前
Qt/QML + C++ 双向数据绑定(MVVM 模式的几种常用方法(ChatGPT)
开发语言·c++·qt
liu****12 小时前
一.脚手架介绍以及部分工具使用
开发语言·数据结构·c++·手脚架开发