一、什么是建造者模式?
- 建造者模式(Builder Pattern),也称为生成器模式,是一种创建型设计模式。
- 与之前学习的工厂方法模式和抽象工厂模式不同,建造者模式更关注对象构建的步骤与过程,而不是单纯的结构或分类。
- 它适合用于构建复杂对象,尤其是当该对象的构造涉及多个组成部分或配置步骤,并且我们希望灵活地组合这些部分以生成不同变种的对象。
二、建造者模式的核心思想
将一个复杂对象的构造过程与其表示分离,使得同样的构造过程可以创建不同的表示(即不同配置的对象)。
- 建造者模式通过拆分构造步骤,让开发者可以按需、灵活地组合各个部分,从而构造出多样化的对象。
- 强调的是“如何一步一步构建出对象”,而不是一次性通过一个庞大的构造函数生成。
三、以游戏关卡制作为例理解建造者模式
1. 场景描述
- 我们正在开发一款战斗闯关类游戏,游戏由多个**关卡(Level)**组成。
- 每个关卡包含以下要素(即对象的组成部分):
- 敌人(Enemies)
- 障碍物(Obstacles)
- 道具(Items)
2. 关卡类的基本结构
class Level {
public:
std::vector<Enemy> enemies;
std::vector<Obstacle> obstacles;
std::vector<Item> items;
};
- 直接在构造函数中为这些字段赋值会缺乏灵活性,尤其是当我们要生成多种不同配置的关卡时(如简单、困难、特殊事件关卡等)。
3. 建造者模式解决方案
(1) 抽象建造者(Builder Interface)
- 定义一个抽象接口
LevelBuilder(关卡生成器),约定构建关卡所需的各个步骤方法:addEnemies(...)addObstacles(...)addItems(...)getLevel():返回最终构建完成的 Level 对象
相当于定义了“我要能设置敌人、障碍、道具,最后能拿到一个完整的关卡”的能力。
(2) 具体建造者(Concrete Builder)
- 实现抽象建造者接口,如
SimpleLevelBuilder(简单关卡生成器)。 - 在具体实现中,将传入的内容添加到对应的
Level对象中,比如:- 将敌人列表加入
enemies - 将障碍物加入
obstacles - 将道具加入
items
- 将敌人列表加入
- 最后通过
getLevel()返回构建完成的关卡对象
(3) 导演类(Director,可选)
- 负责控制建造步骤的执行顺序,调用建造者的方法来按步骤构造对象。
- 可以配置不同的建造者(如简单/困难建造者),从而生成不同类型的关卡。
- 导演类也可以接收一个
Builder对象作为参数,从而实现同一套构建流程,生成不同内容/难度的关卡。
导演类相当于一个“包工头”,它知道先做什么后做什么,但不关心具体是谁来做(即哪个具体的建造者)。
(4) 客户端调用
- 客户端代码通过导演类或直接操作建造者对象,来一步步构造出所需的关卡对象。
- 可以灵活地生成多种变种的关卡,而无需修改关卡类本身或构造函数。
四、建造者模式的构成要素总结
| 要素 | 说明 | 示例(游戏关卡场景) |
|---|---|---|
| 目标产品(Product) | 最终要构建的复杂对象 | Level(关卡对象,包含敌人/障碍/道具) |
| 抽象建造者(Builder Interface) | 定义构建产品各个部分的接口方法 | LevelBuilder,包含 addEnemies()、addObstacles()、getLevel() |
| 具体建造者(Concrete Builder) | 实现抽象建造者,负责实际构建过程 | SimpleLevelBuilder,实现各方法并填充具体内容 |
| 导演类(Director,可选) | 控制建造流程,调用建造者方法,组织构建步骤 | 可配置不同建造者,生成不同关卡;也可省略 |
🎯 关键点: 建造者模式通过拆分构造步骤 + 封装构建过程,让我们可以灵活地构造复杂对象的不同变种。
五、建造者模式的优点
- 简化构造参数
- 拆分单个类的构造任务到多个生成器步骤,避免函数臃肿。
- 灵活组合步骤
- 通过对构造任务的单一职责拆分,我们可以解耦构造过程,从而使用组合灵活地产出更多变种的产品。
- 动态感知构造过程
- 借助导演,可以在运行时根据建造过程调整各部分任务,暂缓创建或执行递归构造。
六、建造者模式的缺点
-
类的数量增多
- 引入了抽象建造者、具体建造者、可能还有导演类,导致整体类结构变复杂
- 对于简单对象,使用建造者模式可能显得“杀鸡用牛刀”
-
代码复杂度上升
- 相比直接使用构造函数或工厂模式,建造者模式的设计层次更丰富,理解成本略高
-
灵活性带来的代价
- 虽然灵活,但也增加了构建过程的控制逻辑,需合理设计以避免过度设计
⚠️ 注意: 这些缺点也是大多数设计模式共有的“通病”——为了更高的灵活性和扩展性,引入了更多的抽象和类。
七、建造者模式的典型应用场景
1. 游戏开发
- 游戏关卡生成
- 游戏角色创建
- 技能系统、装备合成等复杂对象的构造
2. HTTP 请求构造
- 构建一个 HTTP 请求,通常需要设置:
- URL
- 请求方法(GET/POST)
- 请求头(Headers)
- 请求体(Body)
- 使用建造者模式可以链式地、按步骤地设置这些参数,最后发起请求
3. 复杂配置对象 / 配置文件构建
- 比如构建一个 JSON 配置、XML 文件、数据库连接配置等
- 各部分参数多且可选,适合拆分构造步骤
4. 游戏/应用中的场景加载与反序列化
- 从文件加载复杂场景数据,可能涉及递归解析、对象树构建、数据校验等
- 导演类可负责统一流程控制,建造者负责具体节点的创建
八、建造者模式 vs 其他创建型模式
| 对比维度 | 工厂方法模式 | 抽象工厂模式 | 建造者模式 |
|---|---|---|---|
| 关注点 | 创建单一产品,强调“由谁创建” | 创建一族相关产品,强调“多维度分类” | 创建复杂对象,强调“构建步骤与过程” |
| 适用场景 | 产品类型单一,如不同角色的武器 | 多维度产品族,如武器+防具 | 构造复杂对象,如关卡、请求、配置等 |
| 核心目标 | 简化对象创建,统一创建接口 | 提供成套相关对象的创建能力 | 分步骤构造复杂对象,支持灵活组合 |
| 灵活性 | 适用于简单对象创建 | 适用于多系列产品构造 | 适用于构造过程复杂、需灵活配置的对象 |
九、总结
- 建造者模式是一种专注于复杂对象构造步骤与过程的创建型设计模式
- 核心在于将对象的构造过程拆分为多个步骤,并通过建造者类进行封装
- 通过引入抽象建造者、具体建造者、可选的导演类,我们可以灵活地构造出多种变种的复杂对象
- 优点包括:构造灵活、避免参数膨胀、支持多样化配置、代码清晰可维护
- 缺点则是类的数量增加、设计复杂度上升
- 建造者模式在游戏开发(如关卡、角色、技能)、网络请求、配置管理等领域有广泛应用

被折叠的 条评论
为什么被折叠?



