美文网首页
python的装饰器为什么需要函数里面定义函数?

python的装饰器为什么需要函数里面定义函数?

作者: 飘渺的心意 | 来源:发表于2018-12-11 22:31 被阅读17次

    对装饰器接触过的同学都知道,一般写装饰器的时候会定义一个内部的wrapper函数

    def decorate(func):  # 传入函数名当然是因为python处处皆是对象
        def wrapper(a, b):
            print('*'*30)
            return func(a, b)
        return wrapper
    
    @decorate
    def add(a, b):
        return a + b
    
    if __name__ == '__main__':
        print(add(1, 2))
    

    输出

    ******************************
    3
    

    如果这么写,不去调用add函数

    def decorate(func):
        print('run')
        def wrapper(a, b):
            print('*'*30)
            return func(a, b)
        return wrapper
    
    @decorate
    def add(a, b):
        return a + b
    
    # if __name__ == '__main__':
    #     print(add(1, 2))
    

    输出

    run
    

    所以这里必须定义内部函数,这属于python的闭包

    而且为什么是return wrapper而不是return wrapper()?

    return wrapper可以理解为返回wrapper函数的指针

    返回给add方法,在调用add方法的时候相当于执行了wrapper方法,所以wrapper也需要和add方法传入同样的参数

    如果不传参:

    def decorate(func):
        def wrapper():
            print('*'*30)
            return func()
        return wrapper
    
    @decorate
    def add(a, b):
        return a + b
    
    if __name__ == '__main__':
        print(add(1, 2))
    

    它报的错是wrapper函数需要参数

    TypeError: wrapper() takes 0 positional arguments but 2 were given
    

    而且不调用add方法的时候wrapper也不会被执行(因为返回的仅仅是指针)

    如果

    print(add.__name__)
    

    输出

    wrapper
    

    当然如果想参数传递更通用,可以

    def decorate(func):
        def wrapper(*args, **kwargs):
            print('*'*30)
            return func(*args, **kwargs)
        return wrapper
    

    相关文章

      网友评论

          本文标题:python的装饰器为什么需要函数里面定义函数?

          本文链接:https://www.haomeiwen.com/subject/yqryhqtx.html