2、裝飾器html
裝飾器能夠在給函數修改功能的同時並不改變這個函數自己。(如下用的都是python2.7)python
首先,在python裏面函數是對象,在下面的函數裏"fun"是函數也是對象能夠傳遞給test。加括號才能執行函數[1]。python2.7
def fun(): print "run a test fun()" fun() #fun() 是執行函數 #輸出 "run a test fun()" test = fun #fun 是函數,能夠進行傳遞 test() #test() 也能夠執行函數 #輸出 "run a test fun()"
如今要給函數 fun() 修改增長一點功能, 可是又不改變fun() 這個函數自己,這時候能夠用下面的 modify 函數對 fun() 進行調用,這函數
這樣既不改變 fun() 自己,還能增長功能。spa
def fun(): print "run a test fun()" def modify(function): #這裏的參數function能夠用傳遞函數 print "modify" function() #所以傳遞的參數能夠在這裏執行 modify(fun) #在這傳遞函數fun() #輸出 #modify #run a test fun() test = modify test(fun) #輸出 #modify #run a test fun()
如今把上面的代碼用簡潔的方式實現相同的功能,只要把@加上函數名放在要修改的函數前面就有相同的功能,注意用來修飾的函數也就是下面的modify函數必需要有參數,而這個參數就是用來傳遞原來的函數用的。這個功能就是裝飾器,等於減小了手動建立原函數的過程。code
(下面會出現一點問題)htm
def modify(function): print "modify" function() @modify def fun(): print "run a test fun()" fun() #可是這裏執行不能用fun()了,得用fun #輸出 #拋出異常fun()TypeError: 'NoneType' object is not callable
fun
#輸出
#modify
#run a test fun()
這裏若是要用fun() 執行函數的話,得將modify 函數改變一下, 在modify 函數裏的function返回,改爲以下對象
def modify(function): print "modify" return function @modify def fun(): print "run a test function" fun() #輸出 #modify #run a test function
爲何會出現上面問題呢,接下要講講這個@+函數名的語法糖的工做原理blog
...(暫時沒有找到講原理的參考文)io
參考:
[1] Mr.Seven
http://www.cnblogs.com/wupeiqi/articles/4980620.html
--------------------謝謝大佬打賞--------------------------