装饰器为什么不能使用内置函数?

时间:2019-06-23 11:21:08

标签: python decorator python-decorators built-in

我正在学习如何在Python中使用装饰器,并且对此有很深的了解,但是我有一个问题-为什么不能对内置函数使用装饰器?

为什么这样做:

def decorator1(func):
    def inner(*args, **kwargs):
        print("<>=========================<>")
        func(*args, **kwargs)
        print("<>=========================<>")
    return inner

@decorator1
def greet():
    print("Hello!")


greet()

不是这个吗?:

def decorator1(func):
    def inner(*args, **kwargs):
        print("<>=========================<>")
        func(*args, **kwargs)
        print("<>=========================<>")
    return inner

@decorator1
print("Hello!")

是因为在现场执行了打印功能,并且仅定义了greet()函数并且仅在@decorator1之后运行了吗?

1 个答案:

答案 0 :(得分:6)

@decorator的语法只能与def ... function definitionclass ... class definition语句一起使用。这并不意味着您不能“装饰”内置函数。

但是,您尝试将语法应用于expression statementprint()函数的语法。最多可以修饰返回值(对于print()函数,返回值始终为None。)

装饰者不过是calls。语法

@decorator_expression
def functionname(...): ...

执行为

def functionname(...): ...

functionname = decorator_expression(functionname)

但没有将functionname分配两次。

因此要装饰print,请显式调用装饰器:

decorated_print = decorator1(print)
decorated_print("Hello!")

注意:我在这里明确选择了一个不同的名称,以将装饰器函数的结果分配给该名称。如果您确实愿意,您也可以使用print = decorator1(print)。但是随后您可能需要稍后运行del print来取消隐藏内置功能,或使用syntactic sugar重新访问原始功能。

演示:

>>> def decorator1(func):
...     def inner(*args, **kwargs):
...         print("<>=========================<>")
...         func(*args, **kwargs)
...         print("<>=========================<>")
...     return inner
...
>>> decorated_print = decorator1(print)
>>> decorated_print("Hello!")
<>=========================<>
Hello!
<>=========================<>