Домой Edit me on GitHub

2017-09-19

Декораторы

Декоратор подменяет функцию, например мы можем подменить функцию foo на ноль.

def zero(func):
    return 0

@zero
def foo():
    return "Hi"

print(foo)  # 0
print(foo())  # Вызовет ошибку как-будто мы хотим вызвать ноль 0()

Это равносильно следующему коду:

def foo():
    return "Hi"

foo = 0

print(foo)  # 0
print(foo())  # Вызовет ошибку как-будто мы хотим вызвать ноль 0()

Подменим функцию на другую:

def zero(func):
    return lambda: 0

@zero
def foo():
    return "Hi"

print(foo())  # 0

Теперь foo это lambda: 0, а foo() соответственно 0. Это равносильно следующему коду:

def foo():
    return "Hi"

foo = lambda: 0
print(foo())  # 0

И более практичный пример, дополним нашу функцию:

def world(func):
    return lambda: func() + " World!"

@world
def foo():
    return "Hi"

print(foo())  # Hi World!

@world
def hello():
    return "Hello"

print(hello())  # Hello World!

Этот пример уже сложнее переписать:

def foo():
    return "Hi"

foo = lambda: foo() + " World!"
print(foo())  # RuntimeError: maximum recursion depth exceeded
def foo():
    return "Hi"

hello_world = lambda: foo() + " World!"
print(bar())  # Hello World!
Previous: Форматированные строки Next: Декораторы для корутин в asyncio