装饰器是一个对函数进行修饰,添加附加功能的函数。装饰器在不改变函数源代码和调用方式的原则下,添加附加功能。
接下来我们尝试用以前学过的高阶函数函数嵌套函数闭包来实现装饰器。
#高阶函数尝试实现不改代码不改调用方式给函数附加功能
import time
def timer():
time.sleep(2)
def func(f):
stop_time=time.time()
f()
start_time=time.time()
print(start_time-stop_time)
return f
func=func(timer)
func();#多调用了一次timer不合格,改变了附加功能效果
两次执行不能达到预想效果,怎末才能让func=func(timer)时不让func内部目标步骤执行,但又得让func()时执行内部目标步骤呢?函数嵌套可以解决。
#融合函数嵌套后
import time
def func(f):
def w():
start_time=time.time()
f()
stop_time=time.time()
print(stop_time-start_time)
return w
def timer():
time.sleep(2)
timer=func(timer)
timer()
这样一来,在timer=func(timer)时便不会执行目标步骤,而在timer()时可以执行。真实的装饰器还简化了timer=func(timer)
事先在函数前@以下装饰器,以后调用的函数就是装饰的函数
def func(f):
def w():
start_time=time.time()
res=f()
stop_time=time.time()
print(stop_time-start_time)
return res
return w
@func
def timer():
time.sleep(2)
return "timer"
print(timer())
假如待装饰函数有参数:
#对含参函数的修饰器
def discribe(f):
def mid(*args):
print("修饰内容")
res=f(*args)
return res
return mid
@discribe#fun=discribe(fun)
def fun(x,y):
time.sleep(1)
return x+y
@discribe
def fun1(x,y,z):
time.sleep(1)
return x+y+z
print(fun(1,2))#实际是调用mid(1,2),mid内部调用旧fun(1,2)
print(fun1(2,4,1))#实际上调用mid(2,4,1),mid内部调用旧fun(2,4,1)
以下为用装饰器生成器模拟cookie
cookie={'name':'','passwd':''}
member=[{'name':"wwt",'passwd':"123"},{'name':'yyt','passwd':'456'}]
items=['袜子','鞋子','饼干','蛋糕']
def automember():
for i in member:
yield i
def discribe(fun):
def mid(*args):
if ''==cookie['name']:
name=input("name:")
passwd=input("password:")
res=automember()
num=0
while True:
i = res.__next__()
if name==i['name'] and passwd==i['passwd']:
cookie['name']=name
cookie['passwd']=passwd
fun(*args)
break
else:fun(*args)
return mid
@discribe
def loginafter():
print("welcome to this !")
@discribe
def youritems(*args):
print("items:")
print(args)
loginafter()
youritems(*items)