工厂模式详细讲解

一、工厂模式的定位

工厂模式是创建型设计模式的核心,核心思想是将对象的创建与使用分离:把对象创建的复杂逻辑封装在"工厂类"中,业务代码(调用方)只需通过工厂获取对象,无需关注对象的实例化细节(如构造函数参数、子类选择等)。它主要解决了"直接new对象导致的代码耦合、扩展困难"问题,同时让代码更符合开闭原则和单一职责原则。主要分为简单工厂、工厂方法、抽象工厂三种形式,适配不同的业务场景。

二、分类讲解

  1. 简单工厂
  • 定义:由一个单一的工厂类,根据传入的参数动态创建对应产品实例(不属于GoF官方23种设计模式,是工厂方法的简化版)。
  • 举例:RPG游戏中,用 SimpleCharacterFactory 接收 "warrior" / "mage" 参数,内部通过 switch 判断,分别创建 Warrior / Mage 对象。
  • 优点:简化对象创建,调用方只需传参;缺点:新增角色(如弓箭手)需修改工厂类的 switch 逻辑,违反开闭原则,仅适合产品类型少且变动少的场景。
  1. 工厂方法
  • 定义:定义抽象工厂接口,让具体工厂子类决定实例化哪个产品类,把对象实例化延迟到子类。
  • 举例:先定义抽象工厂 CharacterFactory ,再为战士、法师分别创建 WarriorFactory 、 MageFactory 子类,每个子类重写 createCharacter 方法创建对应角色。
  • 优点:新增角色只需加产品类和对应工厂子类,无需改原有代码,符合开闭原则;缺点:产品和工厂一一对应,产品过多时会产生大量工厂类,增加代码复杂度。
  1. 抽象工厂
  • 定义:创建相关/依赖的产品族,而非单一产品,接口中定义多个产品的创建方法。
  • 举例:RPG游戏中,"角色+武器"是产品族: HumanFactory 创建人类战士+人类剑, ElfFactory 创建精灵弓箭手+精灵弓,抽象工厂 RaceFactory 定义 createCharacter 和 createWeapon 两个接口。
  • 优点:保证产品族内对象的兼容性;缺点:新增产品(如防具)需修改抽象工厂接口,所有具体工厂都要同步修改,扩展成本高。

三种工厂模式对比表

模式类型 工厂类特点 产品创建逻辑 开闭原则兼容性
简单工厂 单一工厂类,静态方法 工厂内部判断参数 不兼容
工厂方法 抽象工厂+多个具体工厂子类 子类实现创建逻辑 兼容
抽象工厂 抽象工厂+产品族工厂子类 子类创建产品族 产品族扩展兼容

三、代码实现(三种工厂模式)

cpp 复制代码
#include<iostream>
#include<memory>
#include<string>
using namespace std;

class Character{
protected:
    string name;
    int health;
    int attack;
    int magic;

public:
    Character(const string& n,int h,int a,int m )
    :name(n),health(h),attack(a),magic(m){}

    virtual ~Character()=default;

    virtual void showInfo() const{
        cout<<"角色:"<<name<<endl;
        cout<<"血量:"<<health<<endl;
        cout<<"攻击力:"<<attack<<endl;
        cout<<"魔力:"<<magic<<endl;
    }
    virtual void specialSkill()=0;

    string getName() const{return name;}
};

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

    void specialSkill()override{
        cout<<name<<"使用【狂暴攻击】!"<<endl;
    }
    
    void showInfo()const override{
        cout<<"=== 战士 ==="<<endl;
        Character::showInfo();
        cout<<"特长:近战攻击,高血量"<<endl;
    }
};

//具体角色类 - 法师
class Mage : public Character{
public:
    Mage(const string& name):Character(name,80,30,120){}

    void specialSkill()override{
        cout<<name<<"释放【豪火球】!"<<endl;
    }

    void showInfo()const override{
        cout<<"=== 法师 ==="<<endl;
        Character::showInfo();
        cout<<"特长:魔法攻击,高魔力"<<endl;
    }
};

//具体角色类 - 弓箭手
class Archer : public Character{
public:
    Archer(const string& name):Character(name,100,70,50){}

    void specialSkill()override{
        cout<<name<<"使用【穿透射击】!"<<endl;
    }

    void showInfo()const override{
        cout<<"=== 弓箭手 ==="<<endl;
        Character::showInfo();
        cout<<"特长:远程攻击,平衡属性"<<endl;
    }
};

/****************************简单工厂***************************/
enum CharacterType{
    WARRIOR,
    MAGE,
    ARCHER,
};

class SimpleCharacterFactory{
public:
    static unique_ptr<Character>
    CreateCharacter(CharacterType type,const string &name){
        switch(type){
        case WARRIOR:
            return make_unique<Warrior>(name);
        case MAGE:
            return make_unique<Mage>(name);
        case ARCHER:
            return make_unique<Archer>(name);
        default:
        throw invalid_argument("未知的角色类型");
        }
    }
};

/*******************************工厂方法*******************************/
class CharacterFactory{
protected:
    virtual void setupCharacter(Character* character){
        cout<<"角色"<<character->getName()<<"创建完成,进行基础设置..."<<endl;
    }
public:
    virtual ~CharacterFactory()= default;
    virtual unique_ptr<Character> createCharacter(const string &name) = 0;

    unique_ptr<Character> createCharacterWithSetup(const string &name){
        auto character=createCharacter(name);
        setupCharacter(character.get());
        return character;
    }
};

class WarriorFactory : public CharacterFactory{
protected:
    virtual void setupCharacter(Character* character){
        CharacterFactory::setupCharacter(character);
        cout<<"为战士配备铁剑和盾牌..."<<endl;
    }
public:
    virtual unique_ptr<Character> createCharacter(const string &name){
        return make_unique<Warrior>(name);
    }
};

class MageFactory : public CharacterFactory{
protected:
    virtual void setupCharacter(Character* character){
        CharacterFactory::setupCharacter(character);
        cout<<"为法师配备魔法书和法杖..."<<endl;
    }
public:
    virtual unique_ptr<Character> createCharacter(const string &name){
        return make_unique<Mage>(name);
    }
};

class ArcherFactory : public CharacterFactory{
protected:
    virtual void setupCharacter(Character* character){
        CharacterFactory::setupCharacter(character);
        cout<<"为弓箭手配备弓箭和箭筒..."<<endl;
    }
public:
    virtual unique_ptr<Character> createCharacter(const string &name){
        return make_unique<Archer>(name);
    }
};

/********************************抽象工厂*****************************/
//抽象装备类
class Equipment{
public:
    virtual ~Equipment() = default;
    virtual string getDescription() const = 0;
};

//具体装备类
class HumanSword : public Equipment{
public:
    string getDescription() const override{
        return "人族青钢剑";
    }
};

class HumanShield : public Equipment{
public:
    string getDescription() const override{
        return "人类骑士盾";
    }
};

class ElfBow : public Equipment{
public:
    string getDescription()const override{
        return "精灵月光弓";
    }
};

class ElfCloak : public Equipment{
public:
    string getDescription() const override{
        return "精灵隐身斗篷";
    }
};

//抽象工厂 - 种族工厂
class RaceFactory{
public:
    virtual ~RaceFactory()=default;
    virtual unique_ptr<Character> createWarrior(const string& name) = 0;
    virtual unique_ptr<Character> createArcher(const string& name) = 0;
    virtual unique_ptr<Equipment> createWeapon() = 0;
    virtual unique_ptr<Equipment> createArmor() = 0;
    virtual string getRaceName() const = 0;
};

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

    void showInfo() const override{
        cout<<"=== 人族战士 ==="<<endl;
        Character::showInfo();
        cout<<"特长:均衡发展,适应力强"<<endl;
    }
};

class ElfArcher : public Archer{
public:
    ElfArcher(const string& name):Archer(name+"(精灵)"){}

    void showInfo() const override{
        cout<<"=== 精灵弓箭手 ==="<<endl;
        Character::showInfo();
        cout<<"特长:敏捷过人,箭术精悍"<<endl;
    }
};

//具体工厂类 - 人族工厂
class HumanFactory : public RaceFactory{
public:
    unique_ptr<Character> createWarrior(const string& name)override{
        return make_unique<HumanWarrior>(name);
    }

    unique_ptr<Character> createArcher(const string& name)override{
        return make_unique<Archer>(name+"(人族)");
    }

    unique_ptr<Equipment> createWeapon()override{
        return make_unique<HumanSword>();
    }

    unique_ptr<Equipment> createArmor()override{
        return make_unique<HumanShield>();
    }

    string getRaceName() const override{
        return "人族";
    }
};

//具体工厂类 - 精灵工厂
class ElfFactory : public RaceFactory{
public:
    unique_ptr<Character> createWarrior(const string& name)override{
        return make_unique<Warrior>(name);
    }

    unique_ptr<Character> createArcher(const string& name)override{
        return make_unique<ElfArcher>(name+"(精灵)");
    }

    unique_ptr<Equipment> createWeapon()override{
        return make_unique<ElfBow>();
    }

    unique_ptr<Equipment> createArmor()override{
        return make_unique<ElfCloak>();
    }

    string getRaceName() const override{
        return "精灵";
    }
};

int main()
{
    cout<<"=== 工厂模式对比演示 ==="<<endl;

    cout<<"\n1.简单工厂 - 集中式创建:"<<endl;
    cout<<"优点:实现简单,使用方便"<<endl;
    cout<<"缺点:违反开闭原则,拓展需要修改工厂类"<<endl;
    auto simpleWarrior=SimpleCharacterFactory::CreateCharacter(CharacterType::WARRIOR,"简单战士");
    cout<<"创建结果:"<<simpleWarrior->getName()<<endl;

    cout<<"\n2.工厂方法 - 多态创建:"<<endl;
    cout<<"优点:符合开闭原则,易于扩展"<<endl;
    cout<<"缺点:需要创建多个工厂类"<<endl;
    auto methodFactory = make_unique<WarriorFactory>();
    auto methodWarrior = methodFactory->createCharacterWithSetup("方法战士");
    cout<<"创建结果:"<<methodWarrior->getName()<<endl;

    cout<<"\n3.抽象工厂 - 产品族创建:"<<endl;
    cout<<"优点:可以创建相关产品族,保证产品兼容性"<<endl;
    cout<<"缺点:扩展产品族较困难"<<endl;
    auto abstractFactory = make_unique<HumanFactory>();
    auto abstractWarrior = abstractFactory->createWarrior("抽象战士");
    auto abstractWeapon = abstractFactory->createWeapon();
    cout<<"创建结果:"<<abstractWarrior->getName()<<" + "<<abstractWeapon->getDescription()<<endl;
    return 0;
}

运行结果:

相关推荐
oradh1 天前
Oracle闪回技术操作总结
数据库·oracle·oracle闪回技术操作总结·oracle闪回·flashback技术
别动我齐刘海1 天前
机器人运动控制学习2——基础进阶
c++·人工智能·神经网络·学习·目标检测·机器学习·机器人
ltl1 天前
RocksDB 并发 Compaction 与 Rate Limiter
数据库
傻啦嘿哟1 天前
英雄联盟皮肤爬虫:爬取全皮肤价格与特效,做比价工具
java·c++·爬虫
码匠许师傅1 天前
【C++ 面试真题】24. 聊聊 C++ 的时间日期处理
java·c++·面试
闻道且行之1 天前
图片处理助手|泊松融合原理 + C++ 工程实现,seamlessClone 三模式一次讲透
数据库·c++·人工智能·opencv
夏炳辉.1 天前
PostgreSQL 高可用集群核心配置参数全解:从原生流复制到 Patroni 企业级方案
数据库·postgresql
莫浅子1 天前
day01-USB架构与枚举
c++·单片机·嵌入式驱动
小欣加油1 天前
leetcode3069 将元素分配到两个数组中I
数据结构·c++·算法·leetcode·职场和发展
不会代码的小猴1 天前
7. JSON
开发语言·c++·笔记·qt·算法·json