先看个例子
|
|
从这个例子看来,真正执行的是hello函数,func函数作为参数传给了hello函数。
那么直接执行hello(func)会怎么样呢?
|
|
看来程序将hello(func)的返回值当作一个函数来执行了,然而我们的hello函数并没有设置返回值……
我们来改进一下:
|
|
这时,hello(func)的返回值就成为wrapper()函数,这时再执行hello(func)()就相当于执行wrapper()函数。
装饰器本质上就是被装饰的函数当作一个参数,被传入装饰器函数执行。在执行函数功能之前或之后,
可以利用装饰器,执行函数功能之外的任务。比如,资源状态的校验,残留资源的清理等。
带参数的装饰器
|
|
最外层的sayHelloTo()函数用来处理装饰器的参数传入。
real_proc_wrapper()才是真正的装饰器函数,传入被装饰的函数func()作为参数。
使用类装饰器
先上个简单例子,看清楚在装饰过程中的代码执行顺序
|
|
带参数的类装饰器
|
|
有一点要注意:如果类装饰器有参数传入,func就不能从__init__()函数传入,而要从__call__()函数传入。
装饰器的副作用
我们可以看到,在本文第二个示例中,func()函数被装饰过以后返回的函数是wrapper(),而不是我们期望的func():
|
|
为了消除这个隐患可能带来的副作用,Python提供了functools包中叫wraps的decorator。
下面是改进后的示例:
|
|