【软件设计】23 种设计模式解析与实践指南

引言

设计模式(Design Pattern)是软件开发中反复出现的问题的解决方案,由 Erich Gamma 等四人组(GoF)在 1994 年系统化提出。

在软件开发领域,设计模式是解决常见软件设计问题的可复用方案。它们就像是建筑师手中的蓝图,帮助开发者构建高效、可维护和可扩展的软件系统。掌握多种设计模式,能够让开发者在面对不同的项目需求时,灵活地选择合适的模式,从而提高软件的质量和开发效率。

一、设计模式分类

分类 设计模式名称
创建型模式 单例模式、工厂模式、抽象工厂模式、建造者模式、原型模式
结构型模式 适配器模式、桥接模式、组合模式、装饰器模式、外观模式、享元模式、代理模式
行为型模式 责任链模式、命令模式、解释器模式、迭代器模式、中介者模式、备忘录模式、观察者模式、状态模式、策略模式、模板方法模式、访问者模式

二、定义与描述

设计模式 定义与描述 抽象背景 适用场景与现实问题解决
单例模式 确保类仅有一个实例,提供全局访问点 资源管理(如日志、配置、数据库连接) 任务管理器、打印机队列(全局唯一控制)
工厂方法模式 定义创建对象的接口,子类决定实例化哪个类 统一对象创建接口,应对产品族扩展 框架扩展(Spring BeanFactory)、日志系统多实现
抽象工厂模式 提供创建相关或依赖对象的接口,无需指定具体类 管理产品族,保证客户端与具体实现解耦 跨平台 UI 组件(如按钮、文本框)创建
建造者模式 将复杂对象的构建与表示分离,允许相同构建过程创建不同表示 分步构建复杂对象(如配置文件、SQL 查询) 游戏角色创建(属性分步设置)、套餐组合(如汉堡套餐)
原型模式 通过复制现有实例创建新对象 对象创建成本高(如数据库连接池预热) 快速克隆对象(如游戏存档、缓存数据)
适配器模式 转换类接口,使其能协同工作 旧系统与新接口兼容(如不同支付方式) 第三方 API 集成(支付网关适配不同银行接口)
桥接模式 分离抽象与实现,使两者独立变化 多维度扩展(如形状与颜色) 跨平台开发(操作系统与 GUI 组件解耦)
组合模式 将对象组合成树形结构以表示整体 - 部分层次 统一处理单个对象与组合对象 文件系统目录管理、企业组织架构表示
装饰器模式 动态添加职责,不改变原类结构 功能扩展(如咖啡加配料) 日志增强(记录执行时间、异常信息)
外观模式 提供统一接口简化子系统交互 复杂系统对外暴露简单接口 支付系统封装(整合银行、风控、日志等模块)
享元模式 共享大量细粒度对象以节省内存 内存优化(如文本编辑器字符渲染) 游戏角色池(复用相同模型的角色)
代理模式 控制对真实对象的访问 延迟加载、访问控制(如权限验证) 虚拟代理(图片懒加载)、远程代理(跨网络调用)
责任链模式 将请求沿处理链传递,直到有对象处理它 请求处理者动态组合(如审批流程) 请假审批链(主管→部门经理→CEO)
命令模式 将请求封装为对象,支持撤销、排队等操作 操作封装与参数化(如 GUI 命令) 游戏操作记录(支持撤销 / 重做)、任务队列
解释器模式 定义语言的文法及解释器 特定领域语言解析(如正则表达式) 数学表达式计算、自定义配置语言解析
迭代器模式 提供顺序访问聚合对象元素的方法 遍历方式与数据结构解耦 集合遍历(如 Java 的 Iterator)、树结构遍历
中介者模式 用中介对象封装对象间交互 减少对象间直接依赖(如 MVC 中的 Controller) 聊天室消息转发、UI 组件交互(按钮与文本框解耦)
备忘录模式 捕获并恢复对象状态 状态保存与恢复(如游戏存档) 编辑器撤销功能、数据库事务回滚
观察者模式 对象状态变化时通知依赖它的对象 发布 - 订阅机制(如事件监听) 股票价格实时更新、消息推送系统
状态模式 对象行为随状态改变而变化 状态驱动的行为(如订单状态机) 电梯状态控制(运行 / 停止 / 维修)、工作流引擎
策略模式 定义算法族,允许在运行时选择算法 算法动态切换(如排序策略) 支付方式选择(支付宝 / 微信 / 信用卡)、日志级别控制
模板方法模式 定义操作步骤,子类实现具体步骤 流程固定但部分步骤可变(如数据处理流程) 电商订单处理流程(支付→发货→通知)、测试用例基类
访问者模式 封装作用于对象结构的操作 数据结构与操作分离(如报表生成) 编译器语法树遍历、XML 文档解析

三、综合对比

设计模式 优点 缺点 升级版 线程安全支持 核心应用场景
单例模式 控制实例数量,节省资源 全局状态影响测试,扩展性差 枚举单例、线程安全懒加载 需手动实现 日志系统、配置管理、数据库连接池
工厂方法模式 解耦对象创建与使用,支持扩展 子类爆炸问题 结合依赖注入 框架扩展(Spring BeanFactory)、日志系统多实现
抽象工厂模式 统一管理产品族,保证兼容性 新增产品类型需修改抽象类 泛型工厂 跨平台 UI 组件(按钮、文本框)创建
建造者模式 分步构建复杂对象,灵活性高 增加类数量 流式 API 游戏角色创建、套餐组合(汉堡 + 饮料)
原型模式 快速克隆对象,减少创建成本 深拷贝可能引发性能问题 序列化克隆 游戏存档、缓存数据快速复制
适配器模式 兼容不兼容接口,复用旧代码 增加一层间接性 双向适配器 第三方 API 集成(支付网关适配不同银行)
桥接模式 分离抽象与实现,支持独立扩展 设计复杂度高 结合依赖注入 跨平台开发(操作系统与 GUI 组件解耦)
组合模式 统一处理单个对象与组合对象 树形结构遍历可能复杂 透明组合 文件系统目录管理、企业组织架构表示
装饰器模式 动态扩展功能,不改变原类结构 多层装饰影响性能 链式调用、注解增强 日志增强(记录执行时间、异常信息)
外观模式 简化子系统交互,降低依赖 可能成为性能瓶颈 微服务网关 支付系统封装(整合银行、风控、日志)
享元模式 共享对象节省内存 增加系统复杂度 结合缓存机制 游戏角色池(复用相同模型)、文本编辑器字符渲染
代理模式 控制访问,支持延迟加载 增加代理类 动态代理(如 Java 反射) 图片懒加载、远程服务调用
责任链模式 请求处理者动态组合,扩展性强 可能导致请求未被处理 动态责任链 请假审批链(主管→部门经理→CEO)
命令模式 支持撤销、重做、日志记录 命令类数量多 结合备忘录模式 游戏操作记录、任务队列
解释器模式 自定义语言解析灵活 复杂文法性能差 结合语法树优化 数学表达式计算、配置语言解析
迭代器模式 遍历方式与数据结构解耦 可能限制遍历方式 双向迭代器 集合遍历(Java Iterator)、树结构遍历
中介者模式 减少对象间直接依赖 中介者可能过度复杂 事件总线 聊天室消息转发、UI 组件交互
备忘录模式 保存与恢复对象状态 内存消耗大 差异存储 编辑器撤销功能、数据库事务回滚
观察者模式 支持发布 - 订阅机制,松耦合 通知顺序难以控制 响应式编程(RxJava) 股票价格更新、消息推送系统
状态模式 状态驱动行为,避免条件判断 状态类数量多 状态机框架 电梯状态控制、工作流引擎
策略模式 动态切换算法,扩展性强 客户端需了解所有策略 策略工厂 支付方式选择、日志级别控制
模板方法模式 固定流程,子类实现细节 子类必须实现所有抽象方法 钩子方法增强 订单处理流程(支付→发货→通知)、测试用例基类
访问者模式 数据结构与操作分离 新增操作需修改所有访问者 双分派机制 编译器语法树遍历、XML 文档解析

四、综合应用

**(一)、**文档编辑器

场景组合模式 + 装饰器模式 + 策略模式 + 观察者模式

文档编辑器(树形结构管理 + 格式装饰 + 保存策略 + 实时预览)

java 复制代码
// 组合模式:文档结构
interface DocumentComponent {
    void print();
    void accept(Visitor visitor);
}

class TextElement implements DocumentComponent {
    private String content;
    public TextElement(String content) { this.content = content; }
    public void print() { System.out.println(content); }
    public void accept(Visitor visitor) { visitor.visit(this); }
}

class CompositeElement implements DocumentComponent {
    private List<DocumentComponent> children = new ArrayList<>();
    public void add(DocumentComponent component) { children.add(component); }
    public void print() { children.forEach(DocumentComponent::print); }
    public void accept(Visitor visitor) { visitor.visit(this); }
}

// 装饰器模式:格式增强
abstract class FormatDecorator implements DocumentComponent {
    protected DocumentComponent component;
    public FormatDecorator(DocumentComponent component) { this.component = component; }
    public abstract void print();
    public void accept(Visitor visitor) { component.accept(visitor); }
}

class BoldDecorator extends FormatDecorator {
    public BoldDecorator(DocumentComponent component) { super(component); }
    public void print() { System.out.printf("<b>%s</b>", component); }
}

// 策略模式:保存策略
interface SaveStrategy {
    void save(DocumentComponent doc);
}

class HtmlSaveStrategy implements SaveStrategy {
    public void save(DocumentComponent doc) {
        System.out.println("Saving as HTML...");
        doc.accept(new HtmlVisitor());
    }
}

// 观察者模式:实时预览
interface Observer {
    void update(DocumentComponent doc);
}

class PreviewWindow implements Observer {
    public void update(DocumentComponent doc) {
        System.out.println("Preview updated:");
        doc.print();
    }
}

class DocumentManager implements Subject {
    private List<Observer> observers = new ArrayList<>();
    private DocumentComponent document;
    
    public void attach(Observer observer) { observers.add(observer); }
    public void notifyObservers() { observers.forEach(o -> o.update(document)); }
    
    public void setDocument(DocumentComponent doc) {
        this.document = doc;
        notifyObservers();
    }
}

类图:

时序图:

典型组合方案

树形结构 + 动态扩展:组合模式 + 装饰器模式

流程控制 + 算法选择:责任链模式 + 策略模式

数据遍历 + 操作分离:迭代器模式 + 访问者模式

**(二)、**电商订单处理

场景组合模式 + 责任链模式 + 策略模式

电商订单处理(订单拆分 → 多级审批 → 支付方式选择)

java 复制代码
// 组合模式:订单结构
class OrderComponent {
    protected double amount;
    public abstract void process();
}

class CompositeOrder extends OrderComponent {
    private List<OrderComponent> children = new ArrayList<>();
    public void add(OrderComponent child) { children.add(child); }
    public void process() {
        children.forEach(OrderComponent::process);
    }
}

// 责任链模式:审批链
abstract class Approver {
    protected Approver successor;
    public void setSuccessor(Approver successor) { this.successor = successor; }
    public abstract void approve(OrderComponent order);
}

class ManagerApprover extends Approver {
    public void approve(OrderComponent order) {
        if (order.amount < 1000) {
            System.out.println("Manager approved");
        } else if (successor != null) {
            successor.approve(order);
        }
    }
}

// 策略模式:支付方式
interface PaymentStrategy {
    void pay(double amount);
}

class CreditCardStrategy implements PaymentStrategy {
    public void pay(double amount) {
        System.out.printf("Paid $%.2f via Credit Card%n", amount);
    }
}

类图:

时序图:

**(三)、**文件系统遍历

场景组合模式 + 迭代器模式 + 访问者模式

文件系统遍历(目录结构 → 迭代访问 → 统计文件信息)

java 复制代码
// 组合模式:文件系统节点
interface FileSystemNode {
    void accept(FileVisitor visitor);
}

class File implements FileSystemNode {
    private String name;
    public void accept(FileVisitor visitor) { visitor.visit(this); }
}

class Directory implements FileSystemNode {
    private List<FileSystemNode> children = new ArrayList<>();
    public void add(FileSystemNode node) { children.add(node); }
    public void accept(FileVisitor visitor) {
        visitor.visit(this);
        children.forEach(n -> n.accept(visitor));
    }
}

// 迭代器模式:遍历器
class FileSystemIterator implements Iterator<FileSystemNode> {
    private Stack<FileSystemNode> stack = new Stack<>();
    
    public FileSystemIterator(FileSystemNode root) {
        stack.push(root);
    }
    
    public boolean hasNext() {
        return !stack.isEmpty();
    }
    
    public FileSystemNode next() {
        FileSystemNode node = stack.pop();
        if (node instanceof Directory) {
            ((Directory) node).getChildren().forEach(stack::push);
        }
        return node;
    }
}

// 访问者模式:文件统计
class FileVisitor {
    public void visit(File file) {
        System.out.println("File: " + file.getName());
    }
    
    public void visit(Directory directory) {
        System.out.println("Directory: " + directory.getName());
    }
}

类图:

时序图:

典型组合方案

树形结构 + 动态扩展:组合模式 + 装饰器模式

流程控制 + 算法选择:责任链模式 + 策略模式

数据遍历 + 操作分离:迭代器模式 + 访问者模式

相关推荐
是星辰吖~16 分钟前
C语言_数据结构_队列
c语言·数据结构
时雨h26 分钟前
Spring MVC 详细分层和微服务
java·数据结构·数据库·sql
衡玖1 小时前
c语言闯算法--排序
c语言·数据结构·算法
是星辰吖~4 小时前
C语言_数据结构_栈
c语言·数据结构
Seven974 小时前
【设计模式】使用中介者模式实现松耦合设计
java·后端·设计模式
Seven974 小时前
【设计模式】探索状态模式在现代软件开发中的应用
java·后端·设计模式
Seven974 小时前
【设计模式】从事件驱动到即时更新:掌握观察者模式的核心技巧
java·后端·设计模式
Seven975 小时前
【设计模式】责任链模式教你如何优雅地分发任务
java·后端·设计模式
Seven975 小时前
【设计模式】命令模式助力快速添加新命令而不影响现有代码
java·后端·设计模式
z26373056116 小时前
Redis常用数据结构及命令详解:从基础到进阶
数据结构·数据库·redis