当前位置: 首页 > news >正文

Python设计模式:工程实践中的模式应用

Python设计模式:工程实践中的模式应用

1. 技术分析

1.1 设计模式分类

类型模式复杂度适用场景
创建型单例、工厂、建造者低~中对象创建
结构型适配器、装饰器、代理低~中接口适配
行为型观察者、策略、命令算法封装

1.2 Python实现特点

Python的动态特性和内置机制使得某些传统模式可以更简洁地实现:

  • 单例模式 → 模块级实现
  • 装饰器模式 → @decorator语法
  • 上下文管理器 → with语句

2. 核心功能实现

2.1 单例模式

# 方法1: 模块级单例(推荐) # database.py class Database: def __init__(self): self.connection = None def connect(self): if self.connection is None: print("建立数据库连接") self.connection = "conn_123" return self.connection # 全局实例 _db_instance = Database() def get_database(): return _db_instance # 方法2: 元类单例 class SingletonMeta(type): _instances = {} def __call__(cls, *args, **kwargs): if cls not in cls._instances: cls._instances[cls] = super().__call__(*args, **kwargs) return cls._instances[cls] class DatabaseMeta(metaclass=SingletonMeta): def __init__(self): self.connection = None def connect(self): if self.connection is None: print("建立数据库连接") self.connection = "conn_456" return self.connection # 方法3: 装饰器单例 from functools import wraps def singleton(cls): instances = {} @wraps(cls) def get_instance(*args, **kwargs): if cls not in instances: instances[cls] = cls(*args, **kwargs) return instances[cls] return get_instance @singleton class CacheService: def __init__(self): self.cache = {} def get(self, key): return self.cache.get(key) def set(self, key, value): self.cache[key] = value

2.2 工厂模式

from abc import ABC, abstractmethod # 抽象产品 class Model(ABC): @abstractmethod def predict(self, data): pass # 具体产品 class LinearRegressionModel(Model): def __init__(self, lr=0.01): self.lr = lr self.weights = None def predict(self, data): return sum(w * x for w, x in zip(self.weights, data)) def fit(self, X, y): # 简化实现 self.weights = [0.5] * len(X[0]) class DecisionTreeModel(Model): def __init__(self, max_depth=10): self.max_depth = max_depth self.tree = {} def predict(self, data): return 0.5 # 简化实现 # 工厂 class ModelFactory: _registry = {} @classmethod def register(cls, model_type, model_class): cls._registry[model_type] = model_class @classmethod def create(cls, model_type, **kwargs): if model_type not in cls._registry: raise ValueError(f"Unknown model type: {model_type}") return cls._registry[model_type](**kwargs) # 注册模型 ModelFactory.register("linear", LinearRegressionModel) ModelFactory.register("tree", DecisionTreeModel) # 使用 model = ModelFactory.create("linear", lr=0.001) result = model.predict([1.0, 2.0, 3.0])

2.3 策略模式

from abc import ABC, abstractmethod class OptimizationStrategy(ABC): @abstractmethod def optimize(self, data): pass class GradientDescent(OptimizationStrategy): def __init__(self, lr=0.01): self.lr = lr def optimize(self, data): return "GD优化, lr=" + str(self.lr) class AdamOptimizer(OptimizationStrategy): def __init__(self, lr=0.001, beta1=0.9, beta2=0.999): self.lr = lr self.beta1 = beta1 self.beta2 = beta2 def optimize(self, data): return f"Adam优化, lr={self.lr}" class SGDOptimizer(OptimizationStrategy): def __init__(self, lr=0.01, momentum=0.9): self.lr = lr self.momentum = momentum def optimize(self, data): return f"SGD优化, lr={self.lr}, momentum={self.momentum}" class Trainer: def __init__(self, strategy: OptimizationStrategy): self.strategy = strategy def set_strategy(self, strategy: OptimizationStrategy): self.strategy = strategy def train(self, data): return self.strategy.optimize(data) # 使用 trainer = Trainer(GradientDescent(lr=0.01)) print(trainer.train(data)) trainer.set_strategy(AdamOptimizer(lr=0.001)) print(trainer.train(data))

2.4 观察者模式

from collections import defaultdict class EventObserver: def __init__(self): self._handlers = defaultdict(list) def subscribe(self, event, handler): self._handlers[event].append(handler) return lambda: self.unsubscribe(event, handler) def unsubscribe(self, event, handler): if event in self._handlers: self._handlers[event].remove(handler) def emit(self, event, *args, **kwargs): for handler in self._handlers[event]: handler(*args, **kwargs) class TrainingMonitor: def __init__(self): self.observer = EventObserver() self.history = {'loss': [], 'accuracy': []} def on_epoch_end(self, epoch, loss, accuracy): self.history['loss'].append(loss) self.history['accuracy'].append(accuracy) self.observer.emit('epoch_end', epoch=epoch, loss=loss, accuracy=accuracy) # 检查早停 if len(self.history['loss']) > 5: if all(self.history['loss'][-i] >= self.history['loss'][-i-1] for i in range(1, 5)): self.observer.emit('early_stop', epoch=epoch) # 使用 monitor = TrainingMonitor() def save_model(epoch, **kwargs): print(f"保存模型: epoch={epoch}") def send_notification(epoch, loss, **kwargs): print(f"通知: Epoch {epoch}, Loss={loss:.4f}") monitor.observer.subscribe('epoch_end', save_model) monitor.observer.subscribe('epoch_end', send_notification) monitor.observer.subscribe('early_stop', lambda **k: print("早停触发")) # 模拟训练 for epoch in range(10): loss = 1.0 - epoch * 0.1 accuracy = 0.5 + epoch * 0.05 monitor.on_epoch_end(epoch, loss, min(accuracy, 0.99))

2.5 装饰器模式

import time from functools import wraps def log_calls(func): """日志装饰器""" @wraps(func) def wrapper(*args, **kwargs): print(f"调用 {func.__name__}") start = time.perf_counter() result = func(*args, **kwargs) elapsed = time.perf_counter() - start print(f"{func.__name__} 完成, 耗时: {elapsed:.4f}s") return result return wrapper def retry(max_attempts=3, delay=1.0): """重试装饰器""" def decorator(func): @wraps(func) def wrapper(*args, **kwargs): for attempt in range(max_attempts): try: return func(*args, **kwargs) except Exception as e: if attempt < max_attempts - 1: time.sleep(delay) print(f"重试 {attempt + 1}/{max_attempts}") else: raise return wrapper return decorator def cache_result(func): """缓存装饰器""" @wraps(func) def wrapper(*args, **kwargs): cache_key = str(args) + str(kwargs) if not hasattr(wrapper, '_cache'): wrapper._cache = {} if cache_key not in wrapper._cache: wrapper._cache[cache_key] = func(*args, **kwargs) return wrapper._cache[cache_key] return wrapper @log_calls @retry(max_attempts=3, delay=0.5) @cache_result def fetch_data(url): """带日志、重试和缓存的数据获取""" print(f"从 {url} 获取数据") time.sleep(0.5) return {"status": "success", "data": [1, 2, 3]} # 链式调用 result = fetch_data("http://example.com/api") print(result)

2.6 上下文管理器

class DatabaseConnection: """数据库连接上下文管理器""" def __init__(self, dsn): self.dsn = dsn self.connection = None def __enter__(self): print(f"连接数据库: {self.dsn}") self.connection = f"conn_to_{self.dsn}" return self def __exit__(self, exc_type, exc_val, exc_tb): if exc_type: print(f"数据库错误: {exc_val}") print("关闭数据库连接") self.connection = None return False # 不抑制异常 class Transaction: """事务上下文管理器""" def __init__(self, connection): self.connection = connection self.committed = False def __enter__(self): print("开始事务") return self def __exit__(self, exc_type, exc_val, exc_tb): if exc_type: print(f"事务回滚: {exc_val}") self.rollback() return True # 抑制异常 else: self.commit() return False def commit(self): print("提交事务") self.committed = True def rollback(self): print("回滚事务") # 使用 with DatabaseConnection("mydb") as db: with Transaction(db.connection): print("执行SQL操作...") # raise Exception("测试异常") # 组合使用 with DatabaseConnection("mydb") as db: with Transaction(db.connection) as txn: print("执行SQL操作...")

3. 性能对比

3.1 单例模式实现对比

import timeit # 模块级 vs 元类 module_singleton = """ class _Instance: def __init__(self): self.value = None _instance = _Instance() """ metaclass_singleton = """ class SingletonMeta(type): _instances = {} def __call__(cls, *args, **kwargs): if cls not in cls._instances: cls._instances[cls] = super().__call__(*args, **kwargs) return cls._instances[cls] class Instance(metaclass=SingletonMeta): def __init__(self): self.value = None """ # 测试 module_time = timeit.timeit("_instance", setup=module_singleton, number=100000) meta_time = timeit.timeit("Instance()", setup=metaclass_singleton, number=100000) print(f"模块级: {module_time:.4f}s") print(f"元类: {meta_time:.4f}s")

4. 最佳实践

4.1 模式选择指南

场景推荐模式替代方案
全局唯一对象模块级单例依赖注入
对象创建复杂工厂模式Builder
算法可切换策略模式函数参数
事件处理观察者模式asyncio事件
功能扩展装饰器模式mixin

4.2 注意事项

# ✅ 推荐:简单场景用简单实现 # 单例 → 模块级 # 工厂 → 函数+字典注册 # ❌ 避免:过度使用设计模式 # 简单的if-else能解决的问题不需要工厂模式

5. 总结

设计模式应用要点:

  1. 适度使用:不要为了模式而模式
  2. Python风格:善用Python特性简化实现
  3. 组合使用:多个模式可以组合解决复杂问题
http://www.jsqmd.com/news/768713/

相关文章:

  • 容器化与虚拟化:不是替代,而是共生
  • 5分钟搞定Figma到After Effects转换:AEUX免费终极指南
  • 量子误差缓解与BBGKY层次结构在NISQ时代的应用
  • AI智能体大师技能库:从架构设计到工程实践全解析
  • 开源消息镜像插件:解耦多端消息同步,实现高可靠数据分发
  • 基于AI Agent的Cypress智能测试:自然语言驱动自动化测试实践
  • HTML标签
  • 安全加密技能实战指南:从算法原理到密钥管理的最佳实践
  • 从论文到代码:掌握算法复现的四大核心技能与工程实践
  • 小红书内容采集工具终极指南:三步实现无水印批量下载
  • 乌兰察布市厂区交通标线服务商综合评测与选择指南 - 品牌策略师
  • 实测对比:给YOLOv9换上GhostConv模块后,模型体积和推理速度变化有多大?
  • vue基于springboot的房屋租赁续租系统的设计与实现
  • AIOS-Core:AI驱动的全栈开发智能编排框架实战指南
  • RAG技术全景与实践指南:从核心架构到工程化落地
  • 山西以文留学:专业留学申请服务助力学子圆梦世界名校
  • 2026免费图片去水印软件怎么选?手机/电脑免费去水印工具实测对比
  • 2026年保姆级指南:用免费降AI率工具改写AI文章,毕业查重一次过关 - 降AI实验室
  • E-Hentai漫画批量下载工具:5步完成高效下载的完整指南
  • 快速验证想法:用快马AI十分钟搭建推特内容下载器原型
  • SPT-AKI Profile Editor终极指南:高效管理你的逃离塔科夫存档
  • Gemini 3.1 Pro镜像站技术架构升级解析——给开发者的能力变化速览
  • Docker 27存储驱动性能优化(27步企业级Checklist·含eBPF实时监控脚本)
  • MCP协议与OpenClaw工具服务器:为AI智能体构建标准化工具调用能力
  • 深度学习音频处理工具deepaude:统一接口、GPU加速与最佳实践
  • 闽江学院考研辅导班机构推荐:排行榜单与哪家好评测 - michalwang
  • 43-Android系统源码-ExoPlayer 实战 - Android 应用级媒体播放器核心技术
  • 多环境治理:从开发到生产的“最后一公里”平滑之路
  • 优质之选:AI写教材高效工具,保障低查重,让教材编写不再难!
  • Docker Compose + 低代码前端=秒级部署?手把手实现「拖拽即上线」全流程(附GitHub万星脚手架)