前提,我有一段**(乙個函式)。
import需求1:現在,我想計算這段**的執行時間。time
defrun_time():
time.sleep(0.1)
print('
我曾踏足山巔
')
我可以這樣做:
import此時,需求是可以實現的。time
defrun_time():
start_time =time.time()
time.sleep(0.1)
print('
我曾踏足山巔')
end_time =time.time()
run_t = end_time -start_time
print('
執行時間為:
',run_t)
run_time()
需求2:不想如此麻煩
如果有很多個類似的函式需要計算執行時間,那這種方法就會顯得特別繁瑣。
我們可以不修改源**,再定義乙個計算時間的函式,將需要被計算時間的函式名作為引數傳進去,
直接呼叫函式進行計算執行時間,就不需要每個函式裡面都加入相同**了。
下面進行公升級:
importtime
defrun_time():
time.sleep(0.1)
print('
我曾踏足山巔')
defrun_time1():
time.sleep(1)
print('
也曾墮入低谷')
defcalculation(f):
start_time =time.time()
f()end_time =time.time()
run_t = end_time -start_time
print('
執行時間為:
', run_t)
#直接呼叫函式進行計算
需求3:我還想要不修改呼叫方式直接實現時間的計算。
即還是直接呼叫原函式,但是能同時實現原功能以及時間計算的功能。
由此,我們引入裝飾器函式的概念。
python裝飾器就是用來拓展原來函式功能的一種函式,這個函式的特殊之處在於它的返回值也是乙個函式。
使用python的好處就是不用更改原函式**的前提下給函式增加新的功能。
不修改被裝飾函式的呼叫方式,不修改被裝飾函式的源**。
備註:語法糖
import可以看出,在不改變原函式呼叫方式的情況下,也實現了執行時間的計算。time
def run_time(f): #
裝飾器函式
definner():
start_time =time.time()
f()end_time =time.time()
run_t = end_time -start_time
print('
執行時間為:
', run_t)
return
inner
#func = run_time(func)#不修改函式呼叫方式,新增新功能
@run_time#
語法糖,代替賦值呼叫,等價於上一行**
deffunc():
time.sleep(0.1)
print('
hello world')
func()
原函式的原始碼沒有改變,呼叫方式沒有改變,並且追加了新的執行時間計算功能。
如果被裝飾的引數有返回值。
importtime
#裝飾器必定要是乙個閉包函式
defrun_time(f):
definner():
start =time.time()
func_retrun = f() #
func_return = func() 變數接收被裝飾函式的返回值
end =time.time()
print('
被裝飾函式執行時間為:
',end -start)
return
func_retrun
return
inner
@run_time
#被裝飾
函式def
func():
time.sleep(0.1)
print('
hello world')
return
'這是被裝飾函式返回值'#
func = run_time(func) #結果:func = inner
帶有引數的函式裝飾器
def
definner(a):
print('
裝飾器增加的額外內容:hello world')
return f(a)#
返回被裝飾函式的返回值
#f(a)
return
inner
deffunc(a):
print('
被裝飾函式的引數輸入:
',a)
return
'被裝飾函式的返回值:was a day
在這裡加預設引數,還有動態引數亦如是
(time.asctime())
r =f(a,b,c)
return
r
return
inner
deffunc(a,b,c ):
(a,b,c)
return
'被修飾函式返回值
注:其實下例中的被裝飾函式並沒有用到引數。不過你可以根據需求自己來進行試驗,不再贅述。
#import
time
def
def inner(*args,**kwargs):
(time.asctime())
r = f(*args,**kwargs)
return
r
return
inner
deffunc2():
print('''
三更燈火五更雞,
正是男兒讀書時。
黑髮不知勤學早,
白首方恨讀書遲。
''')
r1 = '''
這首詩深入淺出,自然流暢,富含哲理。核心是「黑髮早勤學,白首讀書遲」。
從學習的時間這一角度立意,勸勉年輕人不要虛度光陰,要及早努力學習,免得將來後悔。
在不改變函式呼叫的基礎上在函式的前、後新增功能。
裝飾器函式,f是被裝飾函式
def inner(*args,**kwargs):
'''執行函式之前要做的
'''r = f(*args,**kwargs)
'''執行函式之後要做的
'''return r#
直譯器原則,從上至下,返回值最後才進行輸出
return
inner
#之後要使用裝飾器函式的時候,直接呼叫就可以了
pass
Python學習 函式裝飾器
裝飾器 定義 本質是函式,裝飾其它函式,就是為其它函式新增附件功能。不能修改被裝飾函式的源 不能修改被裝飾函式的呼叫方式。高階函式 函式巢狀 import time deftime func def args,kwargs start time.time func end time.time pri...
Python基礎學習 函式裝飾器
裝飾器是python中非常實用的函式表達法,盡頭我們不講裝飾器原理,只講怎麼應用。裝飾器原理涉及物件導向以及函式本身也可以作為乙個引數被傳遞,原理比較簡單,但由於迴圈巢狀初學者難以理解。既然難以理解,那就先學會怎麼用,有了經驗,理解起來就相對容易了。首先我們要明白,裝飾器內函式是先於被裝飾函式執行的...
python裝飾器 函式裝飾器,類裝飾器
只要實現此 模式,這個obj就叫乙個裝飾器 參考 函式裝飾器 例子 def decorator func def inner args,kwargs print before.res func args,kwargs print after.return res return inner decor...