Python装饰器就是一个函数,它的产生是为了在不改变目标函数结构的基础上为其增加功能,返回值是增加功能后的目标函数。
运行结果:
... helloworld spend time: 1.50203704834e-05当然有时候目标函数(在上面的程序中为helloworld函数)是有参数的,下面做一些微小的改动
import time def get_run_time(method): def wrapper(*args, **kwargs): start = time.time() method(*args, **kwargs) end = time.time() return end - start return wrapper @get_run_time def helloworld(name): print('I\'m {}, helloworld'.format(name)) if __name__ == '__main__': spend = helloworld('wk') print('spend time: {}'.format(spend))运行结果:
... I'm wk, helloworld spend time: 2.09808349609e-05既然装饰器是个函数,那它也是可以有参数的,此时只要将上述代码稍加改动即可
import time def get_run_time(decimal): def wrapper_of_wrapper(method): def wrapper(*args, **kwargs): start = time.time() method(*args, **kwargs) end = time.time() return round(end - start, decimal) return wrapper return wrapper_of_wrapper @get_run_time(decimal=16) def helloworld(name): print('I\'m {}, helloworld'.format(name)) if __name__ == '__main__': spend = helloworld('wk') print('spend time: {}'.format(spend)) # 下面这行先不用看,这是下一个标题的内容 print(helloworld.__name__)增加了控制返回时间精度的功能,其实就是在原基础上多封了一层,最外层是新增的一层,目的是增加一个相对全局变量(能看懂就行了,能力有限,就不扯深的了),在上述代码中是decimal
执行结果:
... I'm wk, helloworld spend time: 4.60147857666e-05 wrapper装饰器返回的函数虽然结构与目标函数相似,但本质已经发生了变话,返回的是另一个函数,看上面程序中print(helloworld.__name__)的输出为wrapper,再看看functools.wraps的效果
import time import functools def get_run_time(decimal): def wrapper_of_wrapper(method): @functools.wraps(method) def wrapper(*args, **kwargs): start = time.time() method(*args, **kwargs) end = time.time() return round(end - start, decimal) return wrapper return wrapper_of_wrapper @get_run_time(decimal=16) def helloworld(name): print('I\'m {}, helloworld'.format(name)) if __name__ == '__main__': spend = helloworld('wk') print('spend time: {}'.format(spend)) # 对比一下,只增加了@functools.wraps print(helloworld.__name__)运行结果:
... I'm wk, helloworld spend time: 2.09808349609e-05 helloworld