设计模式在 Python 中的实战应用
掌握最常用的设计模式及其 Pythonic 实现,知道何时用何时不用
- 掌握单例、工厂、策略、观察者模式
- 理解 Python 特性如何简化设计模式
- 学会识别过度设计
- 了解依赖注入和装饰器模式的实际应用
设计模式不是银弹
设计模式是前人总结的、在特定场景下解决特定问题的成熟方案。新手常犯的错误是「手里拿着锤子看什么都是钉子」——为了用模式而用模式。Python 的动态特性(一等函数、鸭子类型、装饰器、元类)让很多经典模式变得更简单甚至不需要。
GoF 的 23 个设计模式是为 C++/Java 那种静态、冗长的语言设计的。Python 里很多模式能靠几行代码实现,甚至根本不需要。比如策略模式,Java 里得写一堆类,Python 直接传函数就行。学设计模式的重点是搞懂它解决什么问题,不是背类图。
单例模式(Singleton)
确保一个类只有一个实例,并提供全局访问点。常见于配置管理、数据库连接池、日志器。
工厂模式(Factory)
创建对象时不指定具体类,由工厂决定创建哪种实现。适合根据配置、条件创建不同对象。
# 不使用工厂:到处是 if-elif
if notification_type == "email":
sender = EmailSender()
elif notification_type == "sms":
sender = SMSSender()
elif notification_type == "push":
sender = PushSender()
sender.send(message)
# 简单工厂:集中创建逻辑
class NotifierFactory:
_creators = {}
@classmethod
def register(cls, type_name, creator):
cls._creators[type_name] = creator
@classmethod
def create(cls, type_name):
creator = cls._creators.get(type_name)
if not creator:
raise ValueError(f"Unknown type: {type_name}")
return creator()
# 使用
NotifierFactory.register("email", EmailSender)
NotifierFactory.register("sms", SMSSender)
sender = NotifierFactory.create(notification_type)
# 新增类型只需 register,不用改工厂代码(开闭原则)策略模式(Strategy)
定义一族算法,把它们封装起来,使它们可以互相替换。Python 中直接用函数就够了。
# Java 风格:需要策略接口 + 多个实现类(在 Python 中是过度设计)
class DiscountStrategy(ABC):
@abstractmethod
def calculate(self, price): ...
class NoDiscount(DiscountStrategy):
def calculate(self, price): return price
# Pythonic:直接传函数
def calculate_price(price, discount_func=None):
if discount_func:
return discount_func(price)
return price
# 使用
calculate_price(100, lambda p: p * 0.8) # 8折
calculate_price(100, lambda p: p - 20) # 减20
calculate_price(100) # 原价
# 更复杂的策略可以用字典映射
STRATEGIES = {
"percentage": lambda p, r: p * (1 - r),
"fixed": lambda p, a: p - a,
"bogo": lambda p, _: p / 2, # 买一送一
}
def apply_discount(price, strategy, *args):
return STRATEGIES[strategy](price, *args)观察者模式(Observer)
对象状态变了,所有依赖它的对象都会收到通知,自动更新。事件系统、消息通知、GUI信号都是这个模式。
单例:全局唯一资源(配置、连接池)——但优先考虑依赖注入。工厂:根据条件创建不同实现。策略:多种可互换的算法/规则——Python 中优先用函数。观察者:事件驱动、一对多通知。装饰器:增强函数/类行为(Python 有 @语法糖)。适配器:统一不兼容接口。
资深工程师加餐
底层原理 · 大厂视角 · 工程经验,点卡片展开
同步是发起后一直等结果;并发是「同时在推进」,靠切换让多个任务在等待期交错前进;并行是「同一刻真的在多核同时执行」。I/O 任务大部分时间在等,单线程并发就能拿到高吞吐;只有真正吃 CPU 的计算才需要多核并行。面试时能结合场景讲清「瓶颈是等 I/O 还是算」,比背定义更得分。
挑战任务
实现策略模式
用字典映射写支付策略系统,支持微信/支付宝/信用卡三种支付方式,还能随时新增。
课后作业
重构为模式
找一段你写的包含大量 if-elif 的代码,用工厂模式或策略模式重构,对比前后的可读性和可扩展性。