1. 程式人生 > >裝飾器 總結 2018.09.27

裝飾器 總結 2018.09.27

記錄 裝飾 ren pre 如何 lease sql UNC username

1. 什麽是裝飾器
器=》工具
裝飾=>指的是為被裝飾對象添加新功能

裝飾器本身可以是任意可調用的對象=》函數
被裝飾器本身也可以是任意可調用的對象=》函數

目標:寫一個函數來為另外一個函數來添加一個新功能

2.為何要用裝飾器
開放封閉原則:然間一旦上線就應該對修改封閉,對擴展開放
對修改封閉:
1.不能修改功能的源代碼
2.也不能修改功能的調用方式

對擴展開放:
可以為原有功能添加新的功能

目標:就是在遵循1和2原則的前提下為被裝飾對象添加上新功能


3.如何要用裝飾器
1.無參裝飾器的模板:
from functools import wraps
def outter(func):
@wraps(func)
def rapp(*args,**kwargs):
return rapp



2.def cert(cert_type=‘file‘):
def timeer(func):
def times(*args,**kwargs):
if login_status[‘user‘]:
res=func(*args, **kwargs)
return res
if cert_type==‘file‘:
dic_11 = input(‘用戶名>>:‘)
dic_22 = input(‘密碼>>:‘)
if dic_11 in user["name"] and dic_22 in user["password"]:
login_status[‘user‘]=dic_11
res = func(*args, **kwargs)
return res
else:
print(‘用戶名或者密碼錯誤‘)
return times
return timeer





# 裝飾器的語法糖:在被裝飾對象正上方單獨一行寫@裝飾器的名字
# 運行原理:
# python解釋器一旦運行到@裝飾器的名字,就會調用裝飾器,然後將被裝飾函數的內存地址當作參數
#傳給裝飾器,最後將裝飾器調用的結果賦值給原函數名

# import time
#
# def timmer(func): #func=最原始那個home函數的內地址
# def wrapper(*args,**kwargs): #args=(‘egon‘,) kwargs={}
# start=time.time()
# res=func(*args,**kwargs) #最原始那個home函數的內地址(‘egon‘)
# stop=time.time()
# print(‘run time is %s‘ %(stop - start))
# return res
# return wrapper
#
# @timmer #index=timmer(index)
# def index():
# print(‘welcome to index page‘)
# time.sleep(3)
#
# @timmer #home=timmer(home)
# def home(name):
# print(‘welcome %s to home page‘ %name)
# time.sleep(2)
# return 123
#
# index()
# res=home(‘egon‘) # res=wrapper函數的內地址(‘egon‘)
# print(res)
#
#



import time

# 裝飾器模板
def outter(func):
def wrapper(*args,**kwargs):
#在調用函數前加功能
res=func(*args,**kwargs) #調用被裝飾的\也就是最原始的那個函數
#在調用函數後加功能
return res
return wrapper

@outter #index=outter(index) #index=wrapper
def index():
print(‘welcome to index page‘)
time.sleep(3)

index()




疊加多個裝飾器

# 解釋@語法的時候是自下而上運行
# 而執行裝飾器內的那個wrapper函數時的是自上而下
@timmer # index=timmer(wrapper2) #index=wrapper1
@auth # index=auth(最原始的那個index的內存地址) #index=wrapper2
def index():
print(‘welcome to index page‘)
time.sleep(3)

index() #wrapper1()

‘‘‘



# import time
#
# def timmer(func):
# print(‘timmer‘)
# def wrapper1(*args,**kwargs):
# start=time.time()
# res=func(*args,**kwargs) #res=wrapper2(*args,**kwargs)
# stop=time.time()
# print(‘run time is %s‘ %(stop - start))
# return res
# return wrapper1
#
# def auth(func):
# print(‘auth‘)
# def wrapper2(*args,**kwargs):
# inp_user = input(‘please input your username: ‘).strip()
# inp_pwd = input(‘please input your password: ‘).strip()
# if inp_user == ‘egon‘ and inp_pwd == ‘123‘:
# print(‘login successfull‘)
# res=func(*args,**kwargs) # 調用最原始的那個/也就是被裝飾的那個函數
# return res
# else:
# print(‘username or password error‘)
# return wrapper2
#
#
# @auth # index=auth(wrapper1) #index=wrapper2
# @timmer #timmer(最原始的index)返回wrapper1
# def index():
# print(‘welcome to index page‘)
# time.sleep(3)
#
# index() #wrapper2()
#




import time



def outter1(func1): #func1=wrapper2
print(‘outter1‘)
def wrapper1(*args,**kwargs):
print(‘wrapper1‘)
res1=func1(*args,**kwargs) #res1=wrapper2(*args,**kwargs)
return res1
return wrapper1

def outter2(func2): #func2=最原始的那個index的內存地址
print(‘outter2‘)
def wrapper2(*args,**kwargs):
print(‘wrapper2‘)
res2=func2(*args,**kwargs)
return res2
return wrapper2


@outter1 # index=outter1(wrapper2) #index=wrapper1
@outter2 #outter2(最原始的那個index的內存地址) ===> wrapper2
def index():
print(‘welcome to index page‘)
time.sleep(3)

index() #wrapper1()

‘‘‘
outter2
outter1
wrapper1
wrapper2




有參函數

def login(engine=‘file‘): #engine=‘mysql‘
def auth(func): #func=最原始那個index的內存地址
def wrapper(*args,**kwargs):
if current_user[‘username‘]:
print(‘已經登錄過了,無需再次登陸‘)
res=func(*args,**kwargs)
return res

if engine == ‘file‘:
inp_user = input(‘please input your username: ‘).strip()
inp_pwd = input(‘please input your password: ‘).strip()
if inp_user == ‘egon‘ and inp_pwd == ‘123‘:
print(‘login successfull‘)
current_user[‘username‘]=inp_user # 在登陸成功之後立刻記錄登錄狀態
res=func(*args,**kwargs) # res=最原始那個index的內存地址(*args,**kwargs)
return res
else:
print(‘username or password error‘)
elif engine == ‘mysql‘:
print(‘基於mysql的認證機制‘)
elif engine == ‘ldap‘:
print(‘基於ldap的認證機制‘)
else:
print(‘無法識別的認證源‘)
return wrapper
return auth

@login(‘file‘) #@auth # index=auth(最原始那個index的內存地址) #index=wrapper
def index():
print(‘welcome to index page‘)
time.sleep(3)

@login(‘file‘)
def home(name):
print(‘welcome %s to home page‘ %name)
time.sleep(2)
return 123


index() #wrapper()
res=home(‘egon‘)
print(res)



# 有參裝飾器的模板
def outter1(x,y,z):
def outter2(func):
def wrapper(*args,**kwargs):
res=func(*args,**kwargs)
return res
return wrapper
return outter2

補充:所有的數據類型的值自帶布爾值,可以直接當作條件去用,只需要記住布爾值為假的那一些值即可(0,空,None)

裝飾器 總結 2018.09.27