Python裝飾器原理與用法分析
本文實例講述了Python裝飾器原理與用法。分享給大家供大家參考,具體如下:
1、裝飾器的本質(zhì)是函數(shù),主要用來裝飾其他函數(shù),也就是為其他函數(shù)添加附加功能
2、裝飾器的原則:
(1) 裝飾器不能修改被裝飾的函數(shù)的源代碼
(2) 裝飾器不能修改被裝飾的函數(shù)的調(diào)用方式
3、實現(xiàn)裝飾器的知識儲備
(1) Python中函數(shù)即‘變量'
a、變量在Python中的存儲
x='Tomwenxing' y=x
[說明]:
當Python解釋器遇到語句x='Tomwenxing'時,它主要完成了兩樣工作:
1.在內(nèi)存中開辟了一片空間用來存儲字符串‘Tomwenxing'
2.在內(nèi)存從創(chuàng)建了一個名為x的變量,并用它指向字符串‘Tomwenxing'所占據(jù)的內(nèi)存空間(可以理解為房間和房間號的關(guān)系)

而語句y=x意為將變量x對字符串的引用賦值給變量y,即在內(nèi)存中創(chuàng)建一個變量y,并使其指向變量x所指向的內(nèi)存空間

b、函數(shù)在Python中的存儲
def test(): pass
[說明]:
在Python中,函數(shù)的存儲和變量相似,以上面的函數(shù)為例,Python解釋其主要做兩件事:
1.在內(nèi)存中開辟一個內(nèi)存空間,用來存儲函數(shù)代碼的字符串(本例中代碼只有一句:pass)
2.在內(nèi)存中創(chuàng)建一個變量test,用來指向存儲函數(shù)代碼字符串的內(nèi)存空間(相當于test=‘函數(shù)體')

因此說在Python中函數(shù)即變量
(2) 高階函數(shù)(下面兩個條件滿足任何一個即為高階函數(shù))
a、把一個函數(shù)名當做實參傳遞給另外一個函數(shù)
[對裝飾器的影響]:達到“在不修改被裝飾函數(shù)源代碼的情況下為其添加功能”的效果
import time
def bar():
time.sleep(2)
print('in the bar')
def test(func):
start_time=time.time()
func()
stop_time=time.time()
print('函數(shù)的運行時間為:',stop_time-start_time)
test(bar)
運行結(jié)果:
in the bar
函數(shù)的運行時間為: 2.0021145343780518
b、返回值中包含函數(shù)名
[對裝飾器的影響]:達到“不改變函數(shù)的調(diào)用方式“的效果
import time
def bar():
time.sleep(3)
print('in the bar')
def test2(func):
print('新添加的功能')
return func
bar=test2(bar)
bar()
運行結(jié)果:
新添加的功能
in the bar
(3) 嵌套函數(shù):在一個函數(shù)體內(nèi)用def去聲明一個新的函數(shù)(不是調(diào)用)
def foo():
print('in the foo')
def bar(): #聲明一個新的函數(shù),而不是調(diào)用函數(shù)
print('in the bar')
bar()
foo()
運行結(jié)果:
in the foo
in the bar
4、裝飾器的語法:高階函數(shù)+嵌套函數(shù)=》裝飾器 (下面的例子可以用pycharm的調(diào)試器調(diào)試一下,看看代碼的運行順序)
import time
def timer(func):
def deco(*args,**kwargs):#使用了不定參數(shù)
start_time=time.time()
res=func(*args,**kwargs) #運行函數(shù)
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')
運行結(jié)果:
in the test1
運行時間: 3.0001718997955322
-------------分界線------------------------
in the test2 Tomwenxing
運行時間: 3.000171422958374
5、帶參數(shù)的裝飾器
# -*- coding:utf-8 -*-
user,passwd='Tomwenxing','123'
#如裝飾器帶參數(shù),一般是三層嵌套
def auth(auth_type): #第一層的參數(shù)是裝飾器的參數(shù)
def outer_wrapper(func):#第二層的參數(shù)是裝飾器要裝飾的目標函數(shù)
def wrapper(*args,**kwargs):#第三次的參數(shù)是目標函數(shù)的參數(shù)
if auth_type=='local':
username = input('Username:').strip()
password = input('Password:').strip()
if user == username and passwd == password:
print('用戶Tomwenxing已經(jīng)成功登錄!')
res = func(*args, **kwargs) #運行目標函數(shù)
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('函數(shù)的返回值為:',home('wenxing'))
print('----------------------分界線-------------------')
bbs()
運行結(jié)果:
歡迎來到index頁面
----------------------分界線-------------------
Username:Tomwenxing
Password:123
用戶Tomwenxing已經(jīng)成功登錄!
wenxing,歡迎來到home頁面
函數(shù)的返回值為: This is home page
----------------------分界線-------------------
暫不支持這種登錄方式!
更多關(guān)于Python相關(guān)內(nèi)容感興趣的讀者可查看本站專題:《Python數(shù)據(jù)結(jié)構(gòu)與算法教程》、《Python加密解密算法與技巧總結(jié)》、《Python編碼操作技巧總結(jié)》、《Python函數(shù)使用技巧總結(jié)》、《Python字符串操作技巧匯總》及《Python入門與進階經(jīng)典教程》
希望本文所述對大家Python程序設計有所幫助。
相關(guān)文章
Python復制Excel帶有條件格式的單元格sheet實現(xiàn)步驟
這篇文章主要為大家介紹了Python復制Excel帶有條件格式的單元格sheet實現(xiàn)步驟,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪2023-07-07
Python?提取出SQL語句中Where的值兩種方法(示例代碼)
為了提取SQL語句中WHERE子句的值,我們可以利用Python的sqlparse庫,這是一個專門用于解析SQL語句的庫,這篇文章主要介紹了Python?提取出SQL語句中Where的值的方法,需要的朋友可以參考下2024-08-08
Django框架登錄加上驗證碼校驗實現(xiàn)驗證功能示例
這篇文章主要介紹了Django框架登錄加上驗證碼校驗實現(xiàn)驗證功能,結(jié)合實例形式分析了Django框架基于Pillow模塊的圖形驗證碼生成與使用相關(guān)操作技巧,需要的朋友可以參考下2019-05-05
學會用Python實現(xiàn)滑雪小游戲,再也不用去北海道啦
Python除了極少的事情不能做之外,其他基本上可以說全能.,圖形處理、文本處理、數(shù)據(jù)庫編程、網(wǎng)絡編程、web編程、黑客編程、爬蟲編寫、機器學習、人工智能等.接下來我就教大家做一個不用去北海道也可以滑雪的小游戲,需要的朋友可以參考下2021-05-05
Python實現(xiàn)計算文件MD5和SHA1的方法示例
這篇文章主要介紹了Python實現(xiàn)計算文件MD5和SHA1的方法,結(jié)合具體實例形式分析了Python針對文件MD5及SHA1的計算方法,需要的朋友可以參考下2019-06-06
利用Python連接Oracle數(shù)據(jù)庫的基本操作指南
由于之前的在職的公司沒有機會接觸到Oralce數(shù)據(jù)庫,所以就沒有用python連接過Oralce,之前大多集中在連接mysql和sql server,最近在做一下web自動化的工作,所以簡單的記錄一下,下面這篇文章主要給大家介紹了關(guān)于利用Python連接Oracle數(shù)據(jù)庫的基本操作,需要的朋友可以參考下2022-06-06
Python tkinter實現(xiàn)的圖片移動碰撞動畫效果【附源碼下載】
這篇文章主要介紹了Python tkinter實現(xiàn)的圖片移動碰撞動畫效果,涉及Python tkinter模塊操作圖片基于坐標動態(tài)變換與數(shù)值判定實現(xiàn)移動、碰撞檢測等相關(guān)操作技巧,需要的朋友可以參考下2018-01-01

