简而言之,装饰器允许向函数和类组添加丰富的特性,而无需修改它们。
理解@some_decorator和@some_decorator()区别的关键在于前者是装饰器,而后者是返回装饰器的函数(或可调用)。
我相信看到每个案例的实现有助于理解差异:
@some_decorator
def some_decorator(func):
def wrapper(func):
return func(*args, **kwargs)
return wrapper
应用:
@some_decorator
def some_method():
pass
等价性:
some_method = some_decorator(some_method)
@some_decorator()
def some_decorator():
def decorator(func):
def wrapper(*args, **kwargs):
return func(*args, **kwargs)
return wrapper
return decorator
应用:
@some_decorator()
def some_method():
pass
等价性:
some_method = some_decorator()(some_method)
请注意,现在更容易看出@some_decorator() 是一个返回装饰器的函数,而some_decorator 只是一个装饰器。请记住,有些装饰器是为双向工作而编写的。
所以现在你可能想知道为什么我们有这两种情况,而前一个版本看起来更简单。答案是,如果你想将参数传递给装饰器,使用@some_decorator() 将允许你这样做。让我们看看一些实际的代码:
def some_decorator(arg1, arg2):
def decorator(func):
def wrapper(*args, **kwargs):
print(arg1)
print(arg2)
return func(*args, **kwargs)
return wrapper
return decorator
应用:
@some_decorator('hello', 'bye')
def some_method():
pass
等价性:
some_method = some_decorator('hello', 'bye')(some_method)
注意:我认为值得一提的是,装饰器可以实现为函数或类。更多信息请查看this。