【python技巧009】畫圖直觀展示裝飾器的本質(zhì), 來(lái)N層裝飾器都不怕了!
2022-05-11 22:57 作者:阿-岳同學(xué) | 我要投稿

裝飾器怎么用
函數(shù)理解成:“帶窟窿的紙盒子盒子” 裝飾器加工過(guò)程 涂鴉方式 直觀展示 直觀理解裝飾器 會(huì)寫裝飾器 展示一些種裝飾器實(shí)例: ?添加日志、修改參數(shù)位置 ?保險(xiǎn)處理、統(tǒng)計(jì)函數(shù)執(zhí)行次數(shù) ?延遲執(zhí)行函數(shù)、多次執(zhí)行函數(shù) 多層裝飾器 多層裝飾的順序問(wèn)題 帶參數(shù)的裝飾器 類裝飾器
實(shí)現(xiàn)得一些現(xiàn)成的裝飾器
def logger(oldFunc): ??"""夾層裝飾器,給函數(shù)調(diào)用前后加兩個(gè)打印突出顯示""" ??def newFunc(): ????print("~~~~~~~~~~~") ????oldFunc() ????print("~~~~~~~~~~~") ???... ??return newFunc def logger2(oldFunc): ??"""夾層裝飾器,只給頭頂增加一個(gè)打印""" ??def newFunc(): ????print("+++++++++++") ????oldFunc() ???... ??return newFunc def runDouble(oldFunc): ??"""給一個(gè)函數(shù)裝飾,裝飾后這個(gè)函數(shù)就能運(yùn)行兩次了""" ??def newFunc(): ????oldFunc() ????oldFunc() ??return newFunc def counter(oldFunc): ??"""記錄一個(gè)函數(shù)打印了多少次""" ??count = 0 ??def newFunc(): ????nonlocal count ????count += 1 ????oldFunc() ????print(f"這個(gè)函數(shù){oldFunc.__name__}運(yùn)行了{(lán)count}次") ???... ??return newFunc def shield(oldFunc): ??"""防護(hù)盾裝飾器,讓一個(gè)函數(shù)在運(yùn)行中不會(huì)發(fā)生錯(cuò)誤導(dǎo)致程序終止""" ??def newFunc(): ????try: ??????oldFunc() ????except Exception as e: ??????print(f"函數(shù){oldFunc.__name__}出錯(cuò)了", oldFunc, e) ??return newFunc() from functools import lru_cache @lru_cache(None) def func(): ??print("hello") @lru_cache() def func2(): ?... class Check(object): ??"""類裝飾器""" ??def __init__(self, fn): ????""" ???傳入的是被裝飾的原的函數(shù) ???""" ????self.__fn = fn ??def __call__(self, *args, **kwargs):?# 實(shí)現(xiàn)__call__方法,表示對(duì)象是一個(gè)可調(diào)用對(duì)象,可以像調(diào)用函數(shù)一樣進(jìn)行調(diào)用 ????print("登錄")?# 在這之前可以寫登錄代碼 ????self.__fn()
帶參數(shù)的裝飾器
寫法是套了三層def,中間那層def是原來(lái)的裝飾器的那個(gè)(小機(jī)器人)。
import time """ 帶參數(shù)的選擇器 timer() 加小括號(hào)調(diào)用結(jié)束之后,本身會(huì)變成一個(gè)不帶參數(shù)的裝飾器(小機(jī)器人) 然后這個(gè)裝飾器再對(duì)函數(shù)進(jìn)行裝飾 """ def timer(time_type): ?? ??print(time_type) ??if time_type == "min": ????def robot(func): ??????print("func的名字是:", func.__name__) ??????def inner(*args, **kwargs): ????????start = time.time() ????????func(*args, **kwargs) ????????end = time.time() ????????res = end - start ????????print('時(shí)間結(jié)果是:', res) ??????return inner ??else: ????def robot(func): ??????print("func的名字是:", func.__name__) ??????def inner(*args, **kwargs): ????????start = time.time() ????????func(*args, **kwargs) ????????end = time.time() ????????res = end - start ????????print('時(shí)間結(jié)果是:', res) ??????return inner ??return robot @timer('min') def foo(a, b, c): ??print('in foo', a, b, c) foo('a', 'bb', 'ccc')
標(biāo)簽: