這篇文章主要介紹了Python裝飾器原理與用法,結合實例形式分析了Python裝飾器的概念、原理、使用方法及相關操作注意事項,需要的朋友可以參考下
本文實例講述了Python裝飾器原理與用法。分享給大家供大家參考,具體如下:
1、裝飾器的本質是函數,主要用來裝飾其他函數,也就是為其他函數新增附加功能
2、裝飾器的原則:
(1) 裝飾器不能修改被裝飾的函數的原始碼
(2) 裝飾器不能修改被裝飾的函數的呼叫方式
3、實作裝飾器的知識儲備
(1) Python中函數即'變數'
a、變數在Python中的儲存
x='Tomwenxing' y=x
[說明]:
當Python解釋器遇到語句x='Tomwenxing'時,它主要完成了兩樣工作:
1.在記憶體中開闢了一片空間用來儲存字串'Tomwenxing'
# 2.在記憶體從創建了一個名為x的變量,並用它指向字串'Tomwenxing'所佔據的記憶體空間(可以理解為房間和房間號碼的關係)
而語句y=x意為將變數x對字串的引用賦值給變數y,即在記憶體中建立一個變數y,並使其指向變數x所指向的記憶體空間
b、函數在Python中的儲存
def test(): pass
[說明]:
#在Python中,函數的儲存和變數相似,以上面的函數為例,Python解釋其主要做兩件事:
1.在記憶體中開闢一個記憶體空間,用來儲存函數程式碼的字串(本例中程式碼只有一句:pass)
2.在記憶體中建立一個變數test,用來指向儲存函數程式碼字串的記憶體空間(相當於test='函數體')
#因此說在Python中函數即變數
#(2) 高階函數(下面兩個條件滿足任何一個即為高階函數)
a、把一個函數名當做實參傳遞給另一個函數
#[對裝飾器的影響]:達到「在不修改被裝飾函數原始碼的情況下為其添加功能」的效果
import time def bar(): time.sleep(2) print('in the bar') def test(func): start_time=time.time() func() stop_time=time.time() print('函数的运行时间为:',stop_time-start_time) test(bar)
運行結果:
in the bar
函數的運行時間為: 2.0021145343780518
b、傳回值中包含函數名稱
[對裝飾器的影響]:達到「不改變函數的呼叫方式「的效果
import time def bar(): time.sleep(3) print('in the bar') def test2(func): print('新添加的功能') return func bar=test2(bar) bar()
運行結果:
##新加入的功能(3) 巢狀函數:在一個函數體內用def去宣告一個新的函數(不是呼叫)in the bar
def foo(): print('in the foo') def bar(): #声明一个新的函数,而不是调用函数 print('in the bar') bar() foo()運行結果:
in the foo4、裝飾器的語法:高階函數巢狀函數=》裝飾器(下面的範例可以用pycharm的偵錯器調試一下,看看程式碼的運行順序)in the bar
import time def timer(func): def deco(*args,**kwargs):#使用了不定参数 start_time=time.time() res=func(*args,**kwargs) #运行函数 stop_time=time.time() print('运行时间:',stop_time-start_time) return res # 若无返回值,则返回None return deco @timer #等价于test1=timer(test1)=deco,即test1()=deco() def test1(): time.sleep(3) print('in the test1') @timer #等价于test2=timer(test2)=deco,即test2(name)=deco(name) def test2(name): time.sleep(3) print('in the test2',name) test1() print('-------------分界线------------------------') test2('Tomwenxing')運行結果:
in the test15、帶參數的裝飾器運行時間: 3.0001718997955322
-------- -----分界線------------------------
in the test2 Tomwenxing
運行時間: 3.000171422958374
# -*- coding:utf-8 -*- user,passwd='Tomwenxing','123' #如装饰器带参数,一般是三层嵌套 def auth(auth_type): #第一层的参数是装饰器的参数 def outer_wrapper(func):#第二层的参数是装饰器要装饰的目标函数 def wrapper(*args,**kwargs):#第三次的参数是目标函数的参数 if auth_type=='local': username = input('Username:').strip() password = input('Password:').strip() if user == username and passwd == password: print('用户Tomwenxing已经成功登录!') res = func(*args, **kwargs) #运行目标函数 return res else: exit('用户名或密码有错误') elif auth_type=='ldap': print('暂不支持这种登录方式!') return wrapper return outer_wrapper def index(): print('欢迎来到index页面') @auth(auth_type='local') #home=wrapper() def home(name): print('%s,欢迎来到home页面' %name) return 'This is home page' @auth(auth_type='ldap') def bbs(): print('欢迎来到bbs页面 ') index() print('----------------------分界线-------------------') print('函数的返回值为:',home('wenxing')) print('----------------------分界线-------------------') bbs()運行結果:
#歡迎來到index頁面------------ ----------分界線-------------------
Username:Tomwenxing
Password:123
使用者Tomwenxing已經成功登入!
wenxing,歡迎來到home頁面
函數的回傳值為: This is home page
----------------------分界線-------------------
暫時不支援這種登入方式!
相關推薦:
以上是Python裝飾器原理與用法分析的詳細內容。更多資訊請關注PHP中文網其他相關文章!