装饰器本质上是一个python函数。它可以让某个函数在不需要做代码变动的情况下增加额外的功能。装饰器的返回值也是一个函数对象。装饰器经常用于有切面需求的场景。如插入日志、性能测试、事务处理、缓存、权限校验等场景。装饰器是解决这类问题的绝佳设计。有了装饰器,我们可以抽离出大量与函数功能本身无关的雷同代码并继续重用。装饰器的作用就是为已经存在的函数对象增加额外的功能。
函数装饰器



使用装饰器极大的复用了代码,但是元函数的原信息不见了。如原函数的docstring,__name__,参数列表等。如下例子:

解决这个问题,需要导入functools.wraps。wraps本身也是一个装饰器。它能把原函数的元信息拷贝到装饰器函数中。

装饰器的顺序
@a
@b
@c
def f():
相当于 f= a(b(c(f)))
带参数的装饰器。用于装饰带有参数的函数。如下:

带有不定参数的装饰器。用于装饰多个参数个数不相同的函数。如下:

多个装饰器:

多个装饰器的执行顺序是从第一个装饰器开始,执行到最后一个装饰器,再执行函数本身。
网友评论