正确理解装饰器

先看一段小例子简单理解下什么是装饰器

定义三个函数, w1函数内定义一个内部函数,w1函数的返回值是一个函数名

def w1(Func):
    def inner():
        print("----------验证------------")
        Func()
    return inner

def f1():
    print("---------f1----------")

def f2():
    print("----------f2----------")

test = w1( f1 )
test()
这相当于将f1函数传递给w1返回一个函数名,用test接收,也相当于test指向inner函数 test()就相当于调用这个inner函数所以执行完结果是

print("----------验证------------")
print("---------f1----------")

但是这样写虽然可以,但是有时候因业务需要可能还不满足需求我们可以将test换成 f1
f1 = w1( f1 )
f1()
这样我们调用起来就比较方便了。

但是这里我们又提出新的要求了,python 里面有没有更便捷的方法能,肯定是有的。
我们直接在f1 和 f2 函数前加上一个装饰器也就是

def w1(Func):
    def inner():
        print("----------验证------------")
        Func()
    return inner
@w1
def f1():
    print("---------f1----------")
@w1
def f2():
    print("----------f2----------")

经测试结果是一样的
f1()
f2()
打印出来的结果为:

print("----------验证------------")
print("---------f1----------")
print("----------验证------------")
print("---------f2----------")

以上是装饰器最简单的一部分应用

多个装饰器

def makeBold( fn ):
    def wrapped():
        print("-----1------")
        return "<b>"+fn()+"</b>"

def makeItalic( fn ):
    def wrapped():
        print("------2------")
        return "<i>"+fn()+"</i>"

@makeBold
@makeItalic
def test3()
    print("------3-----")
    return "hello world 3"

ret = test3()
print(ret)
执行完后结果为:

------1------
------2------
------3------
<b><li>hello world 3</li></b>

附一张前辈们解释的详图
这里写图片描述

这里有两个装饰器,当程序执行到@makeBold的时候,当是识别到下面还有装饰器的时候。这个装饰器就会等待下面的装饰器完成后再执行。也就是先执行@makeItalic,先将test3函数作为参数传递给makeBold(),也就是
t1 = makeItalic(test3),这个装饰器执行到这里的时候makeBold开始起作用,有相当于
这里的 t1也就是makeItalic中的wrapped()这个函数
t1 = makeBold( t1 )相当于t1 = makeBold( wrapped )
之后再执行t1()也就是
最后执行也就是从外面一层一层的执行,t1() 也就是makeBold()中的wrapped()这个函数所以先打印1 执行到”<b>+fn()+”</b>”时候 fn()实际上是makeItalic中的wrapped()这个函数,而这个函数中的fn()又是test3()所以一步步执行下来就是上面的结果

猜你喜欢

转载自blog.csdn.net/jeekmary/article/details/79709572