python中的装饰器我觉的真是太巧妙了,很有意思,得做一下笔记。
函数还是那个函数,该怎么调用还是怎么调用,但在调用时先给你额外做一些其他事。
比如有个需求,用户在调用登陆函数之前要验证用户信息是否正确,验证通过后才能登陆。
这用装饰器可以实现,在调用登陆函数的时候自行调用验证函数:
1 def check(fun): 2 ‘‘‘ 验证函数 ‘‘‘ 3 def check_in(): 4 print("正在验证用户信息。。。") 5 if True: 6 print("验证通过!") 7 return fun() 8 else: 9 print("验证失败!") 10 return check_in 11 12 @check # 相当于: fun = check(fun) 13 def fun(): 14 ‘‘‘ 登陆函数 ‘‘‘ 15 print("正在登陆。。。") 16 17 fun() 18 # 正在验证用户信息。。。 19 # 验证通过! 20 # 正在登陆。。。
上面装饰器的实现我觉得还是得益于闭包的存在和函数对象可以作为实参传递这么些个特性。
注意:在调用被装饰函数之前,装饰器函数就已经执行了:
1 def check(fun): 2 ‘‘‘ 验证函数 ‘‘‘ 3 print("这是一个装饰器函数!") 4 def check_in(): 5 print("正在验证用户信息。。。") 6 if True: 7 print("验证通过!") 8 return fun() 9 else: 10 print("验证失败!") 11 return check_in 12 13 @check # python解释器在执行到这里时,就会执行check(fun),打印上面那句话 14 def fun(): 15 ‘‘‘ 登陆函数 ‘‘‘ 16 print("正在登陆。。。") 17 18 # 结果: 19 # 这是一个装饰器函数!
对于多个装饰器嵌套:
1 def d1(f): 2 print("==============d1===============") 3 def inner1(): 4 print("------inner1-------") 5 return "<d1>" + f() + "<d1>" 6 return inner 7 8 9 def d2(f): 10 print("==============d2===============") 11 12 def inner2(): 13 print("------inner2-------") 14 return "<d2>" + f() + "<d2>" 15 return inner 16 17 @d1 # f = d1(f) 18 @d2 # f = d2(f) 19 def f(): 20 print("------3-------") 21 return ‘haha‘ 22 23 print(f()) 24 25 ‘‘‘ 26 结果是: 27 ==============d2=============== 28 ==============d1=============== 29 ------inner1------- 30 ------inner2------- 31 ------3------- 32 <d1><d2>haha<d2><d1> 33 ‘‘‘
相当于:把下层装饰器的结果作为参数传给上层装饰器
f=d1(d2(f))
f()
怎么理解呢?
就像淘宝卖家寄快递一样,比如买了个水杯,装饰器装饰的过程就是打包水杯的过程,先给水杯套上一个
纸盒子,再将纸盒子外面包一层泡沫,然后放到一个大快递盒子里,贴上发件信息。
对应的是:先打印d2,再打印d1;
调用函数的时候就如同买家收到包裹后,先撕开外面的盒子,再扯掉泡沫,再撕掉里面的纸盒子,取出水杯。
对应的是:-------inner1------、-------inner2-------、-----3-------。
原文:https://www.cnblogs.com/wangyi0419/p/12575883.html