標籤:

裝飾器 | Python高級編程

裝飾器的理解

裝飾器是程序開發中經常會用到的一個功能,用好了裝飾器,開發效率如虎添翼,所以這也是Python面試中必問的問題,但對於好多初次接觸這個知識的人來講,這個功能有點繞,自學時直接繞過去了,然後面試問到了就掛了,因為裝飾器是程序開發的基礎知識,這個都不會,別跟人家說你會Python,看了下面的文章,保證你學會裝飾器。

裝飾器,功能就是在運行原來功能基礎上,加上一些其它功能,比如許可權的驗證,比如日誌的記錄等等。不修改原來的代碼,進行功能的擴展。

比如java中的動態代理,python的註解裝飾器

其實python的裝飾器,是修改了代碼。

多個裝飾器

運行結果:

裝飾器功能

1、引入日誌

2、函數執行時間統計

3、執行函數前預備處理

4、執行函數後清理功能

5、許可權校驗等場景

6、緩存

裝飾器示例

1、無參數的函數

運行結果:

上面代碼理解裝飾器執行行為可理解成

foo = timefun(foo)

foo先作為參數賦值給func後,foo接收指向timefun返回的wrappedfunc

foo()

調用foo(),即等價調用wrappedfunc()

內部函數wrappedfunc被引用,所以外部函數的func變數(自由變數)並沒有釋放

func里保存的是原foo函數對象

2、被裝飾的函數有參數

運行結果:

3、被裝飾的函數有不定長參數

運行結果:

4、裝飾器中的return

此時timefun無返回值,運行結果:

如果修改裝飾器為return func(),則運行結果:

運行結果:

總結

一般情況下為了讓裝飾器更通用,可以有return

裝飾器帶參數,在原有裝飾器的基礎上,設置外部變數

運行結果:

類裝飾器(擴展)

裝飾器函數其實是這樣一個介面約束,它必須接受一個callable對象作為參數,然後返回一個callable對象。在Python中一般callable對象都是函數,但也有例外。只要某個對象重寫了__call__()方法,那麼這個對象就是callable的。

運行結果:

說明:

1.當用Test來裝作裝飾器對test函數進行裝飾的時候,首先會創建Test的實例對象,並且會把test這個函數名當做參數傳遞到__init__方法中,即在__init__方法中的func變數指向了test函數體

2. test函數相當於指向了用Test創建出來的實例對象

3.當在使用test()進行調用時,就相當於讓這個對象(),因此會調用這個對象的__call__方法

4.為了能夠在__call__方法中調用原來test指向的函數體,所以在__init__方法中就需要一個實例屬性來保存這個函數體的引用,所以才有了self.__func = func這句代碼,從而在調用__call__方法中能夠調用到test之前的函數體。

@Testndeftest():nprint("----test---")ntest()nshowpy()n

如果把這句話注釋,重新運行程序,依然會看到"--初始化--"

歡迎關注我們的微信公眾號「人工智慧LeadAI」,ID:atleadai

推薦閱讀:

即將發布的 tornado 2.0 將會帶來哪些特性?
python 中 os._exit(), sys.exit(), exit() 的區別是什麼?
深度學習中的Python語言4:實踐和練習Python基礎概念(jupyter notebook版)
你寫過的最好的 Python 腳本是什麼?

TAG:Python | 装饰器 |