1. 程式人生 > >python高階語法-裝飾器(語法糖)

python高階語法-裝飾器(語法糖)

1.高階函式

在python語言中,引數含有函式名的函式稱之為高階函式。(此時呼叫的函式不加引數,也就是說沒有括號緊跟)

2.裝飾器是什麼

在不改變原始碼的基礎上擴充套件函式需要的新需求,這就是裝飾器。(不改變函式原始碼,這也是裝飾器最基本的原則)

裝飾器,它本身也就是一個函式,應用高階函式實現。

使用時一般把被裝飾的函式的記憶體地址當引數傳入裝飾器函式體,通過引數呼叫被裝飾的函式,獲得或者修改其屬性。

3.裝飾器的使用

一般認為,裝飾器使用遵循一定格式,即:高階函式+高階函式內巢狀函式。

假設有一個需求,我要知道正在執行什麼函式,在執行時輸出。

有一個比較粗暴的方法。

def func1():
    print(func1.__name__)
    pass


def func2():
    print(func2.__name__)
    pass


def func3():
    print(func3.__name__)
    pass


if __name__ == '__main__':
    func1()
    func2()
    func3()

這一定是對的,但是不自然就想到兩個字“封裝”,雖然這和裝飾器大相徑庭,但是兩個概念確實有相通之處。

按照裝飾器原則,可以這樣寫。

def funcname(func):
    def out():
        func()
        print(func.__name__)
    return out


@funcname
def func1():
    pass


@funcname
def func2():
    pass


@funcname
def func3():
    pass


if __name__ == '__main__':
    func1()
    func2()
    func3()

結果是,我們確實實現了這個功能。

4.裝飾器的進一步使用

在之前的這個小實驗中,基本上了解了裝飾器的用途和寫法,然而不是所有的函式都想func1這樣簡單,無引數。

對於含不定引數的函式,引數由收集引數獲取。

def funcname(func):
    def out(*args, **kwargs):
        func(*args, **kwargs)
        print(func.__name__)
    return out


@funcname
def func1(a, b):
    print(a+b)


@funcname
def func2(a, b, c):
    print(a+b+c)


@funcname
def func3(a, b, c, d):
    print(a+b+c+d)


if __name__ == '__main__':
    func1(1, 2)
    func2(1, 2, 3)
    func3(1, 2, 3, 4)

5.裝飾器的多重使用

不同的裝飾器是可以給同一個函式裝飾的,會從最後一個裝飾器開始執行到第一個裝飾器,再執行函式本身。