Decorators

Decorators are functions that alter the functionality of other functions without explicitly modifying them.

Understanding decorators requires one to understand the scope and objectivity of functions themselves.

Functions inside other Functions


In [33]:
def is_even(n):
    if n % 2 == 0:
        print("yea!")
        
    def is_mult_four():
        if n % 4 == 0:
            return "yea, mod4!"
    
    print(is_mult_four())
    print("now in is_even_scope!")

In [32]:
print(is_even(4))


yea!
now in is_even_scope!
None

Returning Functions


In [35]:
def name_me(name):
    def formal():
        print("Sir {}, welcome!".format(name))
        
    def informal():
        print("Hey my friend!")
    
    if name == "friend":
        return informal
    else:
        return formal

In [41]:
x = name_me("friend")

In [40]:
x()


Hey my friend!

In [42]:
y = name_me("someone_else")

In [43]:
y()


Sir someone_else, welcome!

Functions as Arguments


In [57]:
def is_even(n):
    if n % 2 == 0:
        return ("yes", "even")
    else:
        return ("no", "odd")
    
def sentencify(func):
    print("{}, it's {} mate!".format(func[0], func[1]))

In [60]:
sentencify(is_even(3))


no, it's odd mate!

In [61]:
sentencify(is_even(2))


yes, it's even mate!

Decorator

We're going to show an example of a decorator.


In [143]:
def rejection_decorator(func):
    def func_wrapper(name):
        return "Hello {},\n\tWe're sorry to inform about the decision.\n-The Team".format(func(name))
    return func_wrapper

@rejection_decorator
def get_letter(name):
    return name

In [144]:
print(get_letter("John"))


Hello John,
	We're sorry to inform about the decision.
-The Team

Multiple Decorators

A function can have multiple decorators, and thus be altered quite a few times. Let's try an example where be implement bold, italics, and underline tags (that don't actually work), but look like they would have.


In [164]:
def bold_decorator(func):
    def func_wrapper(some_text):
        return "[b]{}[/b]".format(func(some_text))
    return func_wrapper

def italic_decorator(func):
    def func_wrapper(some_text):
        return "[i]{}[/i]".format(func(some_text))
    return func_wrapper

def underline_decorator(func):
    def func_wrapper(some_text):
        return "[u]{}[/u]".format(func(some_text))
    return func_wrapper

@bold_decorator
@italic_decorator
@underline_decorator
def text(some_text):
    return some_text

In [165]:
print(text("Modify me!"))


[b][i][u]Modify me![/u][/i][/b]