Python 裝飾器

目錄

函數(shù)
簡單的裝飾器

函數(shù)

理解裝飾器前疤祭,你首先需要理解函數(shù)是如何工作的冯事;

# 理解函數(shù)
>>> def add_one(number):
...     return number + 1

>>> add_one(2)
3

函數(shù)是一級對象(first-class objects)晓猛,也就是說函數(shù)是可以作為參數(shù)來傳遞使用访敌。

# 函數(shù)是一級對象
def say_hello(name):
    return f"Hello {name}"

def be_awesome(name):
    return f"Yo {name}, together we are the awesomest!"

def greet_bob(greeter_func):
    return greeter_func("Bob")

# say_hello 這個函數(shù)作為參數(shù)被使用
>>> greet_bob(say_hello)    # greet_bob() 與 say_hello 的區(qū)別是一個帶括號舷手,一個沒有括號;其中say_hello函數(shù)只有傳遞的作用拾酝,而greet_bob()函數(shù)是調(diào)用執(zhí)行燕少。
'Hello Bob'
# be_awesome這個函數(shù)作為參數(shù)被使用
>>> greet_bob(be_awesome)
'Yo Bob, together we are the awesomest!'

內(nèi)嵌函數(shù)(inner function)就是在其他函數(shù)中定義函數(shù),例如:

def parent():
    print("Printing from the parent() function")

    def first_child():
        print("Printing from the first_child() function")

    def second_child():
        print("Printing from the second_child() function")

    second_child()
    first_child()
# 調(diào)用parent()函數(shù)
>>> parent()
Printing from the parent() function
Printing from the second_child() function
Printing from the first_child() function

從函數(shù)中返回函數(shù)

用函數(shù)作為返回值蒿囤,例如:

def parent(num):
    def first_child():
        return "Hi, I am Emma"

    def second_child():
        return "Call me Liam"

    if num == 1:
        return first_child
    else:
        return second_child

注意返回的 first_child 不帶括號客们,就是直接返回引用的函數(shù) first_child;相反first_child()是對函數(shù)求值的結(jié)果材诽。

# 接上
>>> first = parent(1)
>>> second = parent(2)

>>> first
<function parent.<locals>.first_child at 0x7f599f1e2e18>

>>> second
<function parent.<locals>.second_child at 0x7f599dad5268>

>>> first()
'Hi, I am Emma'

>>> second()
'Call me Liam'

簡單的裝飾器

裝飾器底挫,其本身接收一個函數(shù)對象作為參數(shù),然后做一些工作后岳守,返回接收的參數(shù)凄敢,供外界調(diào)用。
簡而言之:裝飾器包裝一個函數(shù)湿痢,改變其行為涝缝。

# 裝飾器

def my_decorator(func):
    def wrapper():
        print("Something is happening before the function is called.")
        func()
        print("Something is happening after the function is called.")
    return wrapper

def say_whee():
    print("Whee!")

say_whee = my_decorator(say_whee)


# 調(diào)用say_whee()
>>> say_whee()
Something is happening before the function is called.
Whee!
Something is happening after the function is called.

為了不打擾鄰居休息,下面的例子只在白天運行經(jīng)過修飾的代碼譬重。
如果你試著在夜間調(diào)用say_whee()拒逮,什么也不會發(fā)生。

from datetime import datetime

def not_during_the_night(func):
    def wrapper():
        if 7 <= datetime.now().hour < 22:
            func()
        else:
            pass  # Hush, the neighbors are asleep
    return wrapper

def say_whee():
    print("Whee!")

say_whee = not_during_the_night(say_whee)

語法糖
用say_whee()的方式來修飾顯得有點笨拙臀规,而且裝飾在定義函數(shù)下面隱藏了一些滩援。

def my_decorator(func):
    def wrapper():
        print("Something is happening before the function is called.")
        func()
        print("Something is happening after the function is called.")
    return wrapper

@my_decorator
def say_whee():
    print("Whee!")

@my_decorator 是一種更簡單的寫法 代替say_whee = my_decorator(say_whee)

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市塔嬉,隨后出現(xiàn)的幾起案子玩徊,更是在濱河造成了極大的恐慌,老刑警劉巖谨究,帶你破解...
    沈念sama閱讀 216,919評論 6 502
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件恩袱,死亡現(xiàn)場離奇詭異,居然都是意外死亡胶哲,警方通過查閱死者的電腦和手機畔塔,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,567評論 3 392
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人澈吨,你說我怎么就攤上這事把敢。” “怎么了谅辣?”我有些...
    開封第一講書人閱讀 163,316評論 0 353
  • 文/不壞的土叔 我叫張陵修赞,是天一觀的道長。 經(jīng)常有香客問我桑阶,道長榔组,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 58,294評論 1 292
  • 正文 為了忘掉前任联逻,我火速辦了婚禮,結(jié)果婚禮上检痰,老公的妹妹穿的比我還像新娘包归。我一直安慰自己,他們只是感情好铅歼,可當我...
    茶點故事閱讀 67,318評論 6 390
  • 文/花漫 我一把揭開白布公壤。 她就那樣靜靜地躺著,像睡著了一般椎椰。 火紅的嫁衣襯著肌膚如雪厦幅。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,245評論 1 299
  • 那天慨飘,我揣著相機與錄音确憨,去河邊找鬼。 笑死瓤的,一個胖子當著我的面吹牛休弃,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播圈膏,決...
    沈念sama閱讀 40,120評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼塔猾,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了稽坤?” 一聲冷哼從身側(cè)響起丈甸,我...
    開封第一講書人閱讀 38,964評論 0 275
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎尿褪,沒想到半個月后睦擂,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,376評論 1 313
  • 正文 獨居荒郊野嶺守林人離奇死亡茫多,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,592評論 2 333
  • 正文 我和宋清朗相戀三年祈匙,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 39,764評論 1 348
  • 序言:一個原本活蹦亂跳的男人離奇死亡夺欲,死狀恐怖跪帝,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情些阅,我是刑警寧澤伞剑,帶...
    沈念sama閱讀 35,460評論 5 344
  • 正文 年R本政府宣布,位于F島的核電站市埋,受9級特大地震影響黎泣,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜缤谎,卻給世界環(huán)境...
    茶點故事閱讀 41,070評論 3 327
  • 文/蒙蒙 一抒倚、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧坷澡,春花似錦托呕、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,697評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至斟赚,卻和暖如春着降,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背拗军。 一陣腳步聲響...
    開封第一講書人閱讀 32,846評論 1 269
  • 我被黑心中介騙來泰國打工任洞, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人食绿。 一個月前我還...
    沈念sama閱讀 47,819評論 2 370
  • 正文 我出身青樓侈咕,卻偏偏與公主長得像,于是被迫代替她去往敵國和親器紧。 傳聞我的和親對象是個殘疾皇子耀销,可洞房花燭夜當晚...
    茶點故事閱讀 44,665評論 2 354