To understand a decorator, you have to understand what a closure is.
This can be reached with a closure, which returns the inner function.
def function(a): b = 40 def inner_function(): print(a,b) inner_function() # <-- calls the inner_function # inner function has access to the scope of functionIf you rewrite the inner_function as anonymous lambda function, it's more clear:
def function(a): b = 40 inner_function = lambda: print(a, b) inner_function() # <-- calls the inner_function # inner function has access to the scope of functionDecorators should take a function and modify the behavior (input_values, return_values).
This can be reached with a closure, which returns the inner function.
def square(function): def inner(*args, **kwargs): return function(*args, **kwargs) ** 2 return inner # <- returns the inner function without calling it def foo(): return 42 print(foo()) # the direct call together with the decorator looks like this square(foo)() # <- square(foo) returns inner, inner is called # assign the decorated function to a name square_foo = square(foo) # square_foo is now the function inner # calling square_foo square_foo()To @ sign for the decorator is just a syntactical sugar for us.
@wrapper def func(): return # is the same like def func(): return func = wrapper(func) # old name is overwritten by inner function
Almost dead, but too lazy to die: https://sourceserver.info
All humans together. We don't need politicians!
All humans together. We don't need politicians!