装饰器

应用场景:在原有函数的基础上,增加一点功能

例如:下面代码在返回值前面增加字符串‘当前时间:’

1 import time
2 def getXXXTime()
3 return time.strftime('%Y_%m_%d %H:%M:%S',time.localtime())

装饰代码:

 1 import time
 2 
 3 # 定义一个装饰器函数
 4 def sayLocal(func):
 5     def wrapper():
 6         print('当地时间:', end='') 
7
return func() 8 return wrapper 9 10 def getXXXTime(): 11 return time.strftime('%Y_%m_%d %H:%M:%S',time.localtime()) 12 13 14 print(getXXXTime()) 15 # 装饰 getXXXTime 16 getXXXTime = sayLocal(getXXXTime) 17 18 print (getXXXTime()) 19 20 # 结果 21 2020_04_14 20:55:49 22 当地时间:2020_04_14 20:55:49

便捷语法:

1 @sayLocal
2 def getXXXTime():
3     return time.strftime('%Y_%m_%d %H:%M:%S',time.localtime())

被装饰的函数有参数:

  例如:

1 import time
2 def getXXXTimeFormat1(name):
3     curTime = time.strftime('%Y-%m-%d %H:%M:%S',time.localtime())
4     return f'{curTime} ,数据采集者:{name} '
5 
6 
7 def getXXXTimeFormat2(name,place):
8     curTime = time.strftime('%Y-%m-%d %H:%M:%S',time.localtime())
9     return f'{curTime} ,数据采集者:{name} , 采集地:{place}'

  可以使用函数的可变参数:

 1 import time
 2 
 3 def sayLocal(func):
 4     def wrapper(*args, **kargs):
 5         curTime = func(*args, **kargs)
 6         return f'当地时间: {curTime}'
 7     return wrapper
 8 
 9 @sayLocal
10 def getXXXTimeFormat1(name):
11     curTime = time.strftime('%Y-%m-%d %H:%M:%S', time.localtime())
12     return f'{curTime} ,数据采集者:{name} '
13 
14 @sayLocal
15 def getXXXTimeFormat2(name, place):
16     curTime = time.strftime('%Y-%m-%d %H:%M:%S', time.localtime())
17     return f'{curTime} ,数据采集者:{name} , 采集地:{place}'
18 
19 print(getXXXTimeFormat1('张三'))    
20 print(getXXXTimeFormat2('张三',place='北京'))    
21 
22 # 运行结果
23 当地时间: 2020-04-14 21:10:49 ,数据采集者:张三 
24 当地时间: 2020-04-14 21:10:49 ,数据采集者:张三 , 采集地:北京

多个装饰器装饰同一个函数:

 1 def add_auth(func):
 2     print("---开始进行装饰权限1的功能---")
 3     def call_func(*args, **kwargs):
 4         print("---这是权限验证1---")
 5         return func(*args, **kwargs)
 6     return call_func
 7 
 8 def set_func(func):
 9     print("---开始进行装饰权限2的功能---")
10     def call_func(*args, **kwargs):
11         print("---这是权限验证2---")
12         return func(*args, **kwargs)
13     return call_func
14     # return call_func()
15 
16 @add_auth
17 @set_func
18 def demo():
19     print("----test1----")
20 
21 demo()

  运行结果:

1 ---开始进行装饰权限2的功能---
2 ---开始进行装饰权限1的功能---
3 ---这是权限验证1---
4 ---这是权限验证2---
5 ----test1----

从运行结果可以看出:

  • 越靠近原函数的装饰器(代码从上往下,原函数上最后一个@符后的名称)越先装饰
  • 越远离原函数的装饰器越先执行,装饰器都执行完成之后再执行原函数
  • 多个装饰器装饰同一个函数相当于给原函数包多层,先执行的包住后执行的,最后包住原函数执行的代码。

类装饰器:

 1 class Test(object):
 2 
 3     def __init__(self, func):
 4         self.func = func
 5 
 6     def __call__(self, *args, **kwargs):
 7         print("这是装饰器添加的功能......")
 8         return self.func(*args, **kwargs)
 9 
10 
11 @Test
12 def get_str():
13     return '哈哈哈'
14 
15 print(get_str())

  运行结果:

1 这是装饰器添加的功能......
2 哈哈哈
posted @ 2020-04-14 21:17  组装梦想  阅读(133)  评论(0编辑  收藏  举报