Python/Decorator

From Fundamental Ramen
Jump to navigation Jump to search
TODO Code
Using build function to create a decorator.
import datetime
import time

def build_decorator(func, wrapper):
    def func_wrapper(*args, **kwargs):
        return wrapper(*args, **kwargs)
    def class_wrapper(func):
        def method_wrapper(*args, **kwargs):
            return wrapper(*args, **kwargs)
    if func is None:
        return class_wrapper
    return func_wrapper

def print_time(func, suffix = '>>'):
    def wrapper(*args, **kwargs):
        isotime = datetime.datetime.now().strftime('%H:%M:%S')
        print('begin at:', isotime, suffix)
        func(*args, **kwargs)
        isotime = datetime.datetime.now().strftime('%H:%M:%S')
        print('end at:', isotime, suffix)
    return build_decorator(func, wrapper)

@print_time
def func_job(a, b=1):
    print('a={}, b={}'.format(a, b))
    time.sleep(1)

class Something:
    @print_time
    def method_job(self, c, d=1):
        print('c={}, d={}'.format(c, d))
        time.sleep(1)

func_job(1, b=3)
Something().method_job(2, d=4)
def pre_hook(func):
    def wrapper(*args):
        a = args[0] + 1
        b = args[1] + 1
        return func(a, b)
    return wrapper
def post_hook(func):
    def wrapper(*args):
        print(func(*args))
    return wrapper
def duo_hook(func):
    def wrapper(*args):
        a = args[0] + 1
        b = args[1] + 1
        sum = func(a, b)
        print(sum)
        return sum
    return wrapper
def mydeco(func=None, name='default'):
    state = {
        'begin': 0
    }

    def pre_task():
        state['begin'] = time.time()
        print('name=%s' % name)

    def post_task():
        elapsed = time.time() - state['begin']
        print('elapsed=%.2f' % elapsed)

    def func_wrapper(*args):
        pre_task()
        fret = func(*args)
        post_task()
        return fret

    def deco_wrapper(func):
        def func_wrapper(*args):
            pre_task()
            fret = func(*args)
            post_task()
            return fret
        return func_wrapper

    return deco_wrapper if func is None else func_wrapper

@mydeco
def test1():
    time.sleep(3)

@mydeco(name="noname")
def test2():
    time.sleep(1)