本文摘自php中文网,作者不言,侵删。
本篇文章给大家带来的内容是关于Python中装饰器是什么?Python中装饰器的介绍,有一定的参考价值,有需要的朋友可以参考一下,希望对你有所帮助。一、什么是装饰器
装饰器,decorator,本质上是一个Python函数,它可以让其他函数在不需要做任何代码变动的前提下增加额外功能,装饰器的返回值也是一个函数对象。
装饰器通过不修改核心代码而增强核心代码部分的功能。例如在函数前插入日志、权限校验、事务处理等场景。
而且可以抽离出大量与函数功能无关的雷同代码并重用。
二、早期实现:不是装饰器的装饰器
例如:
1 2 3 4 5 6 | def foo():
print ( "2017-06-08" )
f = foo # 将函数赋值给变量,f为函数对象
f()
# 返回结果:
2017-06-08
|
三、语法糖@ 实现简单装饰器
假设现在要增强foo()的功能,例如,在函数调用前打印日志。但是又不希望修改foo()函数的定义。在这种代码运行期间动态增加功能的方式,称之为“装饰器”。
如下:
1 2 3 4 5 6 7 8 9 10 11 | def testfunc(func):
print ( 'testfunc' )
def wrapper():
print ( "%s %s() called" %(time.ctime(),func.__name__))
return func()
return wrapper
@testfunc
def foo():
print ( 'foo1()' )
foo() # 相当于执行testfunc(foo) ->wrapper(foo) -> foo()
|
执行结果:
1 2 3 | testfunc
Wed Sep 12 15:01:13 2018 foo() called
foo1()
|
说明:执行foo()前,先执行testfunc(foo),再执行wrapper(),返回时调用foo()本身。
四、接收特定类型参数的装饰器
如下:
1 2 3 4 5 6 7 8 9 10 | def testfunc_with_args(func):
def wrapper_argus(arg1, arg2):
print ( "I got args! Look:" , arg1, arg2)
func(arg1, arg2)
return wrapper_argus
@testfunc_with_args
def full_name(first_name, last_name): # 带参数,将参数传给被装饰的函数
print ( "My name is" , first_name, last_name)
full_name( "Peter" , "Venkman" ) # 调用
|
执行结果:
1 2 | I got args! Look: Peter Venkman
My name is Peter Venkman
|
五、带不定参数的装饰器
当有多个函数需要调用装饰器,但是函数的参数各不同时,该如何实现呢?总不能一个函数对应一个装饰器吧。这时候就可以用带不定参数的装饰器进行实现。
如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | def log(func):
def wrapper(*args,**kwargs): # 可接受各种参数
print ( 'call %s():' % func.__name__)
return func(*args,**kwargs) # 返回一个函数
return wrapper # 装饰器返回一个函数,进入到wrapper()
@log # @log放到now()的定义处,相当于执行语句:now = log(now)
def now_1(a,b):
print ( 'now()1:a+b = ' ,a+b)
@log
def now_2(a,b,c):
print ( 'now_2():a+b+c = ' ,a+b+c)
now_1(1,2)
now_2(1,2,3)
|
运行一下哦~
六、多个装饰器
当一个函数想要加入多项功能时,可以考虑使用多层装饰器,就是要注意一下装饰器的执行顺序。
举个栗子:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | # 注意代码的执行顺序
def deco_1(func):
print ( '------111111------' )
def wrapper(*args,**kwargs): # 包裹函数,参数与原函数的参数一致
print ( 'start: this is deco_1.' )
func(*args,**kwargs)
print ( 'end: deco_1.' )
return wrapper # 返回值是一个包裹函数
def deco_2(func):
print ( '------222222------' )
def wrapper(*args,**kwargs):
print ( 'start: this is deco_2.' )
func(*args,**kwargs)
print ( 'end: deco_2.' )
return wrapper
@deco_1
@deco_2
def now_1(a,b):
print ( 'now()1:a+b = ' ,a+b)
now_1(1,2)
|
运行结果:
1 2 3 4 5 6 7 8 | # 结果,注意执行顺序:
------222222------
------111111------
start: this is deco_1.
start: this is deco_2.
now()1:a+b = 3
end : deco_2.
end : deco_1.
|
七、装饰器本身带参数
除了给被装饰的函数带参数,装饰器本身也可以带参数。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 | def logging(level):
def wrapper(func):
def inner_wrapper(*args, **kwargs):
print ( "[{level}]: enter function {func}()" .format(level=level, func=func.__name__))
return func(*args, **kwargs)
return inner_wrapper
return wrapper
@logging(level= 'INFO' )
def say(something):
print ( "say {}!" .format(something))
@logging(level= 'DEBUG' )
def do (something):
print ( "do {}..." .format(something))
say( 'hello' )
do ( "my work" )
|
执行结果:
1 2 3 4 5 | # 执行结果:
[INFO]: enter function say()
say hello!
[DEBUG]: enter function do ()
do my work...
|
相关推荐:
python中的装饰器详解
Python中的各种装饰器详解
以上就是Python中装饰器是什么?Python中装饰器的介绍的详细内容,更多文章请关注木庄网络博客!!
相关阅读 >>
Python中怎么定义一个类
Python解决pandas处理缺失值为空字符串的问题
Python中类的创建与使用的实现代码详解
Python之io多路复用之epoll
Pythonista3都能做什么
如何利用Python实现购物程序思路以及实现代码
excel转sqlite在Python下实现的方法介绍
Python如何实现敏感词替换
Python分数怎么表示
Python经典算法有哪些
更多相关阅读请进入《Python》频道 >>
人民邮电出版社
python入门书籍,非常畅销,超高好评,python官方公认好书。
转载请注明出处:木庄网络博客 » Python中装饰器是什么?Python中装饰器的介绍