文章目录
Python 装饰器:优雅地增强函数功能
一、什么是装饰器?
装饰器 (Decorator) 是 Python 中的一种特性,允许你在 不修改原始函数代码 的情况下,为其加入新的功能或行为。
它的实质是:一个函数,接收另一个函数作为参数,返回一个新的函数。
二、最简单的装饰器
def my_decorator(func):
def wrapper():
print("函数开始执行")
func()
print("函数执行结束")
return wrapper
@my_decorator
def say_hello():
print("Hello, world!")
say_hello()
三、带参数的装饰器
def log(message):
def decorator(func):
def wrapper(*args, **kwargs):
print(f"[{message}] 函数开始")
result = func(*args, **kwargs)
print(f"[{message}] 函数结束")
return result
return wrapper
return decorator
@log("日志")
def add(a, b):
return a + b
add(3, 5)
四、实际场景
- 日志记录
- 权限校验
- 性能监控
- 缓存 (如 functools.lru_cache)
- Web 路由注册 (Flask, FastAPI)
五、functools.wraps
from functools import wraps
def my_decorator(func):
@wraps(func)
def wrapper(*args, **kwargs):
print("开始")
return func(*args, **kwargs)
return wrapper
六、装饰器装饰类方法
装饰实例方法
def log(func):
def wrapper(self, *args, **kwargs):
print(f"[LOG] {func.__name__}")
return func(self, *args, **kwargs)
return wrapper
class MyClass:
@log
def say_hello(self):
print("Hello from instance")
装饰类方法
def log_classmethod(func):
def wrapper(cls, *args, **kwargs):
print(f"[CLASSLOG] {func.__name__}")
return func(cls, *args, **kwargs)
return wrapper
class MyClass:
@classmethod
@log_classmethod
def do_something(cls):
print("Running...")
装饰静态方法
def log_static(func):
def wrapper(*args, **kwargs):
print(f"[STATICLOG] {func.__name__}")
return func(*args, **kwargs)
return wrapper
class MyClass:
@staticmethod
@log_static
def static_action():
print("Static method")
七、装饰器类 (Decorator Class)
基本示例
class MyDecorator:
def __init__(self, func):
self.func = func
def __call__(self, *args, **kwargs):
print("开始")
result = self.func(*args, **kwargs)
print("结束")
return result
@MyDecorator
def greet(name):
print(f"Hello, {name}!")
带状态的装饰器
class CallCounter:
def __init__(self, func):
self.func = func
self.count = 0
def __call__(self, *args, **kwargs):
self.count += 1
print(f"第 {self.count} 次调用")
return self.func(*args, **kwargs)
带参数的装饰器类
class LogWithPrefix:
def __init__(self, prefix):
self.prefix = prefix
def __call__(self, func):
def wrapper(*args, **kwargs):
print(f"[{self.prefix}] 开始")
result = func(*args, **kwargs)
print(f"[{self.prefix}] 结束")
return result
return wrapper
八、装饰器与异步编程
装饰 async 函数
import asyncio
import functools
def async_logger(func):
@functools.wraps(func)
async def wrapper(*args, **kwargs):
print(f"[ASYNC] {func.__name__} 开始")
result = await func(*args, **kwargs)
print(f"[ASYNC] {func.__name__} 结束")
return result
return wrapper
@async_logger
async def fetch_data():
await asyncio.sleep(1)
print("数据已获取")
asyncio.run(fetch_data())
通用装饰器:同时/异步全支持
import inspect
def smart_logger(func):
if inspect.iscoroutinefunction(func):
async def async_wrapper(*args, **kwargs):
print("[ASYNC] 开始")
result = await func(*args, **kwargs)
print("[ASYNC] 结束")
return result
return async_wrapper
else:
def sync_wrapper(*args, **kwargs):
print("[SYNC] 开始")
result = func(*args, **kwargs)
print("[SYNC] 结束")
return result
return sync_wrapper
九、思维导图
小结
Python 装饰器是很强大的技术,不仅仅是代码优化的工具,更是让你的代码更 Pythonic 的重要手段。
无论是函数装饰器、方法装饰器、装饰器类、还是异步世界下的装饰器,都是 Python 高级技巧的核心组成部分。
如果你熟练装饰器,你不仅仅是在写代码,而是在写有结构、可重用、有风格的 Python 程序。