Skip to content

设计模式

代码的「套路」,前人的智慧结晶。

设计模式不是银弹,不是用得越多越好。但不懂设计模式,你写的代码大概率是「能用但不优雅」的——耦合度高、难以扩展、难以测试。

设计模式的核心价值在于沟通。当你说出「这里用观察者模式实现」,团队里的每个工程师都能立刻理解你的意图,而不需要你画一堆图、写一堆注释去解释。这就是设计模式作为「设计语言」的价值。

这篇文章系列覆盖三大类设计模式(创建型、结构型、行为型),结合 Java/Spring 源码中的实际应用,分析每种模式的核心意图、UML 结构、代码实现,以及适用场景和常见误区,帮助你从「会用」到「用对」的进阶。

模块速览

23 种经典设计模式,按用途分为三类。理解分类背后的逻辑,比单独记住每种模式更重要。

类型核心意图代表模式
创建型对象怎么创建出来单例、工厂、建造者、原型
结构型类和对象怎么组织适配器、装饰器、代理、桥接、组合、外观
行为型对象间的行为怎么协调策略、模板方法、观察者、责任链、命令、迭代器、状态

学习路径建议

第一阶段:理解核心思想(1 周)
→ 理解 SOLID 原则:单一职责、开闭、里氏替换、接口隔离、依赖倒置
→ 理解「组合优于继承」的原则
→ 从 Spring 源码中找设计模式的影子
→ 结合实际项目:你的代码中有哪些可以用设计模式优化?

第二阶段:三大类模式详解(2 周)
创建型(1-2 天)
→ 单例模式:饿汉 vs 懒汉 vs 双重检查锁 vs 静态内部类,DCL 的 volatile 重要性
→ 工厂模式:简单工厂、工厂方法、抽象工厂的区别与适用场景
→ 建造者模式:链式调用、lombok @Builder 的实现原理
→ 原型模式:深拷贝 vs 浅拷贝,clone() 的正确实现

结构型(3-4 天)
→ 适配器模式:类适配器 vs 对象适配器,Wrapper 的本质
→ 装饰器模式:IO 流中的 BufferedInputStream 是怎么装饰的?
→ 代理模式:静态代理 vs JDK 动态代理 vs CGLIB,Spring AOP 的实现原理
→ 桥接模式:JDBC 驱动如何桥接数据库和 Java 程序
→ 外观模式:Service 层是否就是外观模式?

行为型(1 周)
→ 策略模式:消除 if-else,Spring 的 InstantiationStrategy
→ 模板方法:JDBC Template 的 query() 就是模板方法
→ 观察者模式:Spring 事件机制、MQ 的发布订阅
→ 责任链模式:Netty 的 ChannelPipeline、Servlet Filter
→ 命令模式:Runnable、ActionListener 的本质

第三阶段:源码中的设计模式(1 周)
→ Spring:FactoryBean、BeanFactory、AOP(代理)、事务(模板方法)
→ MyBatis:SqlSessionFactoryBuilder(建造者)、Executor(命令模式)
→ Spring MVC:HandlerMapping、ViewResolver
→ JDK:Collections.sort()(策略+模板)、InputStream(装饰器)
→ Guava Cache:LoadingCache(异步装饰器)、RemovalListener(观察者)

为什么设计模式容易用错?

设计模式最常见的误区是「过度设计」——为了用模式而用模式,把简单的代码写得复杂。

一个简单的判断标准:如果这个模式让你的代码更难理解,那就不要用。 设计模式的目的是降低复杂度,而不是增加复杂度。

另一个常见问题是混淆模式。比如代理模式和装饰器模式,结构上几乎一模一样,区别在于意图:

  • 代理模式:控制对对象的访问,侧重「我能不能访问」
  • 装饰器模式:增强对象的行为,侧重「我怎样增强它」

再比如策略模式和模板方法:

  • 策略模式:把算法封装成独立对象,组合使用
  • 模板方法:把算法骨架定好,具体步骤由子类实现,继承使用

理解意图上的区别,比记住 UML 结构更重要。

面试的核心逻辑

设计模式面试分为三个层次:

第一层:会说。 能讲清楚什么是单例模式、工厂模式、代理模式、策略模式。知道它们的 UML 结构。

第二层:会用。 能结合实际场景说出「这里适合用 XXX 模式」并写出代码。知道 Spring 中哪些地方用到了这些模式。

第三层:会用对。 能分析一个模式的优点和局限。比如单例模式在多线程环境下的问题、代理模式带来的性能开销、过度使用工厂模式导致的类爆炸。

"面试官最想看到的,不是你背了多少种设计模式,而是你能不能在合适的场景下,恰到好处地使用它们。『我选择不用设计模式,因为这里直接写更清晰』——这种回答,往往比硬套模式加分。"

基于 VitePress 构建