[英]A more elegant way for this python decorator
Basically I want a decorator with an argument list that contains more than just a function to be able to be called from both the @- and regular forms. 基本上,我希望装饰器具有一个参数列表,该参数列表不仅包含一个函数,而且可以从@-和常规形式中进行调用。 I've "designed" a quick workaround, but it's ugly and executes a function in @-form immediately, which is an undesired side-effect (that's due to return body_two() of course). 我已经“设计”了一个快速的解决方法,但是它很丑陋,并立即以@ -form形式执行一个函数,这是不希望的副作用(这当然是由于返回body_two()所致)。
def status_display_with_comment(comment, closure = None):
def body_one(function = None):
def body_two():
print(comment)
#an ugly workaround to be able to run both the @- and regular forms
if function != None:
print("Entering", function.__name__)
function()
print("Exited", function.__name__)
elif closure != None:
print("Entering", closure.__name__)
closure()
print("Exited", closure.__name__)
return body_two()
return body_one
def a_function():
print('a_function executes')
@status_display_with_comment(comment = 'some comment')
def a_function_with_comment():
print('a_function_with_comment executes')
a_function_status_display_with_comment = status_display_with_comment(closure = a_function, comment = 'a comment')
a_function_status_display_with_comment()
Thanks in advance. 提前致谢。
PS: I have to wrap my head around that whole closure thing. PS:我必须把头放在整个封闭的东西上。 Which is fun considering it could be done recursively like in Scheme (a long time ago for me). 考虑到可以像在Scheme中那样递归完成(很久以前对我来说),这很有趣。
You want a function that returns a decorator: 您需要一个返回装饰器的函数:
def status_display_with_comment(comment):
def decorator(function):
def wrapper():
print(comment)
print("Entering", function.__name__)
result = function()
print("Exited", function.__name__)
return result
return wrapper
return decorator
def a_function():
print('a_function executes')
a_function_SD_WC = status_display_with_comment('a comment')(a_function)
a_function_SD_WC()
Also works: 也可以:
@status_display_with_comment('a comment')
def a_function():
print('a_function executes')
a_function()
The regular, direct decorator already returns a closure: 常规的直接装饰器已经返回了一个闭包:
def a_normal_decorator(function):
def wrapper():
return function()
return wrapper
wrapper
here is a closure since it has to keep function
around even after a_normal_decorator
finished executing. wrapper
是一个闭包,因为即使a_normal_decorator
完成执行后,它也必须保持function
。
For reference, this is how an idiomatic decorator is usually written: 供参考,这是惯用修饰符通常的编写方式:
import functools
def decorator(function):
@functools.wraps(function)
def wrapper(*a, **kw):
return function(*a, **kw)
return wrapper
That is, it passes arguments to the wrapped function and doesn't throw away its return value. 也就是说,它将参数传递给包装的函数,并且不会丢弃其返回值。
functools.wraps
copies from the function being wrapped to the wrapper function __name__
, __module__
, __annotations__
and __doc__
, the documentation string. functools.wraps
从函数副本被包装到包装函数__name__
, __module__
, __annotations__
和__doc__
,文档字符串。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.