装饰器
开放封闭原则
1.对扩展是开放的
我们说,任何一个程序,不可能在设计之初就已经想好了所有的功能并且未来不做任何更新和修改。所以我们必须允许代码扩展、添加新功能。
2.对修改是封闭的
因为我们写的一个函数,很有可能已经交付给其他人使用了,如果这个时候我们对函数内部进行修改,或者修改了函数的调用方式,很有可能影响其他已经在使用该函数的用户。
所以装饰器最终最完美的定义就是:在不改变原被装饰的函数的源代码以及调用方式下,为其添加额外的功能。
装饰器
装饰器的主要功能:在不改变函数调用方式的基础上在函数的前、后添加功能。
装饰器的固定格式
# 装饰器的固定格式 def wrapper(f): # 装饰器函数,f是被装饰的函数 def inner(*args, **kwargs): """在被装饰函数之前要做的事""" ret = f(*args, **kwargs) # 被装饰的函数调用 '在被装饰函数之后要做的事' return ret return inner @wrapper # 语法糖 @装饰器函数名 def func(): # 被装饰的函数 print('Hello World')
无参装饰器(示例)
import time def timmer(func): def wrapper(*args,**kwargs): start_time=time.time() res=func(*args,**kwargs) stop_time=time.time() print('run time is %s' %(stop_time-start_time)) return res return wrapper @timmer def foo(): time.sleep(3) print('from foo') foo()
带参装饰器(示例)
def auth(driver='file'): def auth2(func): def wrapper(*args,**kwargs): name=input("user: ") pwd=input("pwd: ") if driver == 'file': if name == 'egon' and pwd == '123': print('login successful') res=func(*args,**kwargs) return res elif driver == 'ldap': print('ldap') return wrapper return auth2 @auth(driver='file') def foo(name): print(name) foo('egon')
多个装饰器装饰同一个函数
def wrapper1(func): def inner(): print('wrapper1 ,before func') func() print('wrapper1 ,after func') return inner def wrapper2(func): def inner(): print('wrapper2 ,before func') func() print('wrapper2 ,after func') return inner @wrapper2 @wrapper1 def f(): print('in f') f()
带参数的装饰器--500个函数
import time FLAGE = False def timmer_out(flag): def timmer(func): def inner(*args,**kwargs): if flag: start = time.time() ret = func(*args,**kwargs) end = time.time() print(end-start) return ret else: ret = func(*args, **kwargs) return ret return inner return timmer # timmer = timmer_out(FLAGE) @timmer_out(FLAGE) #wahaha = timmer(wahaha) def wahaha(): time.sleep(0.1) print('wahahahahahaha') @timmer_out(FLAGE) def erguotou(): time.sleep(0.1) print('erguotoutoutou') wahaha() erguotou()