(一) 装饰器基础知识
什么是Python装饰器?Python里装饰器是一个可调用的对象(函数),其参数是另一个函数(被装饰的函数)
假如有一个名字为somedecorator的装饰器,target是被装饰的函数:
>>>@somedecorator
...deftarget():
...print("running target")
上面代码的效果和下面的书写一样:
>>> target = somedecorator(target)
@somedecorator只是语法糖,工作原来就是上面这句代码,为了确认这个原理,我们看看下面控制台信息:
>>> defsomedecorator(func):
...definner():
...print("running inner")
...returninner
...>>>@somedecorator
...deftarget():
...print("running target")
...>>>target()
running inner>>>target.inner at 0x7f20829fb950>
>>>
从控制台信息我们可以看到target()语句只输出了somedecorator 里inner()的print,target函数已经被替换为somedocorator的返回值inner函数的引用。
从以上示例我们看到了装饰器第一个特性:能把被装饰的函数替换成其他函数。
下面我们看装饰器的第二个特性:import时执行:
(二)Python何时执行装饰器
我们通过一个示例来看效果:
有如下的py源文件Example7_2.py:
registry =[]defregister(func):print("running register(%s)" %func)
registry.append(func)returnfunc
@registerdeff1():print("running f1")
@registerdeff2():print("running f2")deff3():print("running f3")defmain():print("running main")print("registry ->", registry)
f1()
f2()
f3()if __name__ == "__main__":
main()
register是装饰器,f1和f2被register装饰,f3没有
我们尝试import Example7_2,看看控制台的输出:
>>> importExample7_2
running register()
running register()
从控制台信息我们看到import Example7_2时,@register 就立即执行
我们再运行程序:
#python3 Example7_2.py
running register()
running register()
running main
registry-> [, ]
running f1
running f2
running f3
这里看到被装饰的函数f1,f2在运行时才执行
这就是导入时和运行时的区别,
好了,今天先到这里,再会。