23种设计模式全面解析
设计模式是解决软件设计中常见问题的经典方案。根据《设计模式:可复用面向对象软件的基础》(GoF),23种设计模式分为以下三类:
一、创建型模式(5种)
目标:解耦对象的创建过程,提高系统灵活性
模式名称 | 核心思想 | 典型应用场景 |
---|---|---|
工厂方法 | 定义创建对象的接口,子类决定实例化哪个类 | 数据库连接器、日志记录器 |
抽象工厂 | 创建相关或依赖对象的家族,不指定具体类 | GUI组件库、跨平台系统适配 |
建造者 | 分步构建复杂对象,分离构造与表示 | XML解析器、游戏角色生成器 |
原型 | 通过克隆现有对象来创建新对象 | 对象初始化成本高时的复制操作 |
单例 | 确保类只有一个实例,提供全局访问点 | 配置管理器、线程池、缓存系统 |
二、结构型模式(7种)
目标:组合类或对象形成更大的结构
模式名称 | 核心思想 | 典型应用场景 |
---|---|---|
适配器 | 转换接口使不兼容类协同工作 | 旧系统集成、第三方库封装 |
桥接 | 分离抽象与实现,允许独立变化 | 跨平台绘图引擎、设备驱动程序 |
组合 | 以树形结构处理整体-部分关系 | 文件系统、GUI容器控件 |
装饰器 | 动态添加职责,替代继承扩展功能 | IO流增强、游戏装备系统 |
外观 | 为复杂子系统提供统一的高层接口 | API网关、框架入口类 |
享元 | 共享细粒度对象,减少内存消耗 | 文字编辑器字符对象、棋牌游戏棋子 |
代理 | 为其他对象提供访问代理,控制访问 | 远程调用、虚拟文件系统、权限控制 |
三、行为型模式(11种)
目标:优化对象间的通信与职责分配
模式名称 | 核心思想 | 典型应用场景 |
---|---|---|
责任链 | 将请求沿处理链传递,直到被处理 | 审批流程、异常处理机制 |
命令 | 封装请求为对象,支持撤销/重做操作 | 事务系统、GUI操作历史记录 |
解释器 | 定义语法的表示与解释方式 | 正则表达式引擎、SQL解析器 |
迭代器 | 提供顺序访问集合元素的方法 | 集合遍历、树形结构遍历 |
中介者 | 通过中介对象封装对象间交互 | 聊天室系统、空中交通管制系统 |
备忘录 | 捕获并保存对象内部状态,支持状态回滚 | 文档版本控制、游戏存档系统 |
观察者 | 定义对象间的一对多依赖关系(事件驱动) | 股票行情通知、GUI事件处理 |
状态 | 封装状态相关行为,允许运行时状态切换 | 订单状态机、游戏角色状态管理 |
策略 | 定义算法族,使其可互相替换 | 支付方式选择、排序算法切换 |
模板方法 | 定义算法骨架,子类重写特定步骤 | 框架扩展点、业务流程标准化 |
访问者 | 在不修改类的前提下为类添加新操作 | 编译器语法树分析、报表生成器 |
四、模式选择指南
-
创建型场景
- 需要灵活控制对象创建过程 → 工厂/建造者模式
- 全局唯一访问点 → 单例模式
- 复杂对象复制 → 原型模式
-
结构型场景
- 接口不兼容 → 适配器模式
- 动态功能扩展 → 装饰器模式
- 资源优化 → 享元模式
-
行为型场景
- 事件驱动系统 → 观察者模式
- 算法切换 → 策略模式
- 状态管理 → 状态模式
- 操作记录 → 命令模式
五、经典模式对比
对比维度 | 工厂方法 vs 抽象工厂 | 装饰器 vs 代理 | 策略 vs 状态 |
---|---|---|---|
核心区别 | 生产单个对象 vs 对象家族 | 增强功能 vs 控制访问 | 算法替换 vs 状态驱动行为变化 |
扩展方向 | 垂直扩展(子类化) | 横向扩展(功能叠加) | 算法扩展 vs 状态扩展 |
典型场景 | 单一产品创建 vs 跨平台UI组件库 | IO流增强 vs 远程服务代理 | 支付方式选择 vs 订单状态机 |
六、实际应用建议
-
避免过度设计
- 优先解决实际问题,而非强制使用模式
- 简单if-else能解决的不要用策略模式
-
模式组合使用
- 工厂方法+原型:高效创建复杂对象
- 观察者+命令:实现事件驱动的撤销操作
-
框架集成
- Spring:工厂模式(BeanFactory)
- React:观察者模式(State更新)
- Node.js:中间件模式(责任链变体)
掌握设计模式的关键在于理解其本质思想,而非机械套用。建议结合具体项目实践,从简单模式(如策略、观察者)开始逐步深入,最终达到"无招胜有招"的设计境界。