python装饰器

import functools


# 不带参数的装饰器
def log(func):
    @functools.wraps(func)
    def wrapper(*args, **kw):
        print('call %s' % func.__name__)
        return func(*args, **kw)

    return wrapper


# 带参数的装饰器
def log2(name):
    def decorator(func):
        @functools.wraps(func)
        def wrapper(*args, **kw):
            print('%s call %s' % (name, func.__name__))
            return func(*args, **kw)

        return wrapper

    return decorator


# 兼容带参数和不带参数
def log3(p):
    def build_wrapper(func, name=None):
        @functools.wraps(func)
        def wrapper(*args, **kw):
            print('%s call %s' % (name if name else 'somebody', func.__name__))
            return func(*args, **kw)

        return wrapper

    if callable(p):
        # 不带参数
        return build_wrapper(p)
    else:
        # 带参数
        def decorator(func):
            return build_wrapper(func, p)

        return decorator


@log
def test():
    print('test!')
# 输出:
# call test
# test!


@log2('Tom')
def test2():
    print('test2')
# 输出:
# Tom call test2
# test2


@log3
def test3():
    print('test3')
# 输出:
# somebody call test3
# test3


@log3('Jim')
def test4():
    print('test4')
# 输出:
# Jim call test4
# test4


if __name__ == '__main__':
    test()
    test2()
    test3()
    test4()