成人国产在线小视频_日韩寡妇人妻调教在线播放_色成人www永久在线观看_2018国产精品久久_亚洲欧美高清在线30p_亚洲少妇综合一区_黄色在线播放国产_亚洲另类技巧小说校园_国产主播xx日韩_a级毛片在线免费

資訊專欄INFORMATION COLUMN

python decorators

Yangyang / 578人閱讀

摘要:裝飾器基礎本質本質是語法糖使用來修飾某個函數(shù)時其解釋器會解釋成注意這條語句會被執(zhí)行多重裝飾器相當于帶參數(shù)裝飾器相當于使用給被裝飾函數(shù)傳遞參數(shù)是一個數(shù)組,一個字典帶參數(shù)的裝飾器等同于方法裝飾器類方法是一個特殊的函數(shù),它的第一個參數(shù)指向類實例

python decorators 裝飾器基礎 Decorator 本質

@ 本質是語法糖- Syntactic Sugar
使用@decorator 來修飾某個函數(shù) func 時:

@decorator
def func():
    pass

其解釋器會解釋成:

func = decorator(func)

注意這條語句會被執(zhí)行

多重裝飾器

@decorator_one
@decorator_two
def func():
    pass

相當于:

func = decorator_one(decorator_two(func))

帶參數(shù)裝飾器

@decorator(arg1, arg2)
def func():
    pass

相當于:

func = decorator(arg1,arg2)(func)
使用 *args、**kwargs 給被裝飾函數(shù)傳遞參數(shù)
def wrapper(func):
    def wrapper_in(*args, **kwargs):
        # args是一個數(shù)組,kwargs一個字典
        print("%s is running" % func.__name__)
        return func(*args, **kwargs)
    return wrapper_in

@wrapper
def func(parameter1, parameter2, key1=1):
    print("call func with {} {} {}".format(parameter1, parameter2, key1))


func("haha", None, key1=2)

# func is running
# call func with haha None 2
帶參數(shù)的裝飾器
def log(level):
    def decorator(func):
        def wrapper(*args, **kwargs):
            if level == "warn":
                print("%s with warn is running" % func.__name__)
            elif level == "info":
                print("%s with info is running" % func.__name__)
            return func(*args, **kwargs)
        return wrapper

    return decorator


@log("warn")
def foo(*args, **kwargs):
    print("args {}, kwargs{}".format(args, kwargs))

foo(1, 2, a = 3)

# foo with warn is running
# args (1, 2), kwargs{"a": 3}

等同于

def foo(name="foo"):
    print("args {}, kwargs{}".format(args, kwargs))

foo = log("warn")(foo)
方法裝飾器

類方法是一個特殊的函數(shù),它的第一個參數(shù) self 指向類實例
所以我們同樣可以裝飾類方法

def decorate(func):
   def wrapper(self):
       return "

{0}

".format(func(self)) return wrapper class Person(object): def __init__(self): self.name = "John" self.family = "Doe" @decorate def get_fullname(self): return self.name+" "+self.family my_person = Person() print my_person.get_fullname() #

John Doe

上例相當于固定了 self 參數(shù),不太靈活
使用 *args, **kwargs傳遞給 wrapper 更加通用:

def pecorate(func):
   def wrapper(*args, **kwargs):
       return "

{0}

".format(func(*args, **kwargs)) return wrapper class Person(object): def __init__(self): self.name = "John" self.family = "Doe" @pecorate def get_fullname(self): return self.name+" "+self.family my_person = Person() print my_person.get_fullname()
類裝飾器

類實現(xiàn) __call__ 方法后變成可調用對象,故可以用類做裝飾器

class EntryExit(object):

    def __init__(self, f):
        self.f = f

    def __call__(self):
        print "Entering", self.f.__name__
        self.f()
        print "Exited", self.f.__name__

@EntryExit
def func1():
    print "inside func1()"

@EntryExit
def func2():
    print "inside func2()"

def func3():
    pass

print type(EntryExit(None))
# func1 變?yōu)轭悓嵗?print type(func1)
print type(EntryExit)
# func3 是普通函數(shù)
print type(func3)
func1()
func2()

# 
# 
# 
# 
# Entering func1
# inside func1()
# Exited func1
# Entering func2
# inside func2()
# Exited func2

類裝飾器

@EntryExit
def func1():
    print "inside func1()"

等同于

def func1():
    print "inside func1()"
# 此處可以看出 func1 是類EntryExit的一個實例
func1 = EntryExit(myfunc1)
裝飾器裝飾類
register_handles = []


def route(url):
    global register_handles

    def register(handler):
        register_handles.append((".*$", [(url, handler)]))
        return handler

    return register

@route("/index")
class Index():
    def get(self, *args, **kwargs):
        print("hi")

# Index 仍然為原來定義的類實例
# 相當于在定義類的同時調用裝飾器函數(shù) route, 將該類注冊到全局路由 register_handles
@route("/main")
class Main():
    def get(self, *args, **kwargs):
        print("hi")

print (register_handles)

print(type(Index))

# [(".*$", [("/index", )]), (".*$", [("/main", )])]
# 
@route("/index")
class Index():
    def get(self, *args, **kwargs):
        print("hi")
Index = route("/index")(Index)
# register 返回傳入的 handler,故 Index 仍然為類對象
functools

上述裝飾器實現(xiàn)有個問題,就是被裝飾函數(shù)的屬性被改變

文章版權歸作者所有,未經(jīng)允許請勿轉載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉載請注明本文地址:http://systransis.cn/yun/42700.html

相關文章

  • python 裝飾器 part2

    摘要:裝飾器傳參被裝飾的函數(shù)帶有參數(shù)的情況接上一篇,直接上代碼函數(shù)也就是被裝飾的函數(shù)的運行時間是裝飾器的正確使用,不需要傳參裝飾器的正確使用,需要傳參此時不用再像上面一樣賦值,可以直接調用返回值被裝飾的函數(shù)有返回值在裝飾器內(nèi)部需被裝飾函數(shù)的調用 python 裝飾器 傳參 被裝飾的函數(shù)帶有參數(shù)的情況 接上一篇,直接上代碼 import time def decorator(func): ...

    sanyang 評論0 收藏0
  • Python函數(shù)修飾器---當方法前遇到@參數(shù)化的修飾器方法時發(fā)生的事

    一、前提概念   Python中的函數(shù)是對象。也因此,函數(shù)可以被當做變量使用。 二、代碼模型 以下代碼片段來自于: http://www.sharejs.com/codes/python/8361 # -*- coding: utf-8 -*- from threading import Thread import time class TimeoutEx...

    huashiou 評論0 收藏0
  • Python 裝飾器使用指南

    摘要:裝飾器是可調用的對象,其參數(shù)是另一個函數(shù)被裝飾的函數(shù)。第二大特性是,裝飾器在加載模塊時立即執(zhí)行。另一個常見的裝飾器是,它的作用是協(xié)助構建行為良好的裝飾器。 裝飾器是可調用的對象,其參數(shù)是另一個函數(shù)(被裝飾的函數(shù))。 裝飾器基礎知識 首先看一下這段代碼 def deco(fn): print I am %s! % fn.__name__ @deco def func(): ...

    NeverSayNever 評論0 收藏0
  • Python裝飾器

    摘要:一引用書流暢的書二基本概念問題裝飾器是什么解答嚴格來說,裝飾器只是語法糖,裝飾器是可調用的對象,可以像常規(guī)的可調用對象那樣調用,特殊的地方是裝飾器的參數(shù)是一個函數(shù)問題裝飾器有什么特性解答裝飾器有個特性,一是可以把被裝飾的函數(shù)替換成其他函數(shù), 一, 引用 [書] 流暢的Python [書] Effective Python 二, 基本概念 showImg(https://segme...

    aisuhua 評論0 收藏0
  • Python知識點:理解和使用裝飾器 @decorator

    摘要:使用類裝飾器,優(yōu)點是靈活性大,高內(nèi)聚,封裝性。不過不用擔心,有,本身也是一個裝飾器,它的作用就是把原函數(shù)的元信息拷貝到裝飾器函數(shù)中,使得裝飾器函數(shù)也有和原函數(shù)一樣的元信息。 showImg(https://segmentfault.com/img/bVbrFWb?w=742&h=484);Python的裝飾器(decorator)是一個很棒的機制,也是熟練運用Python的必殺技之一。...

    cyqian 評論0 收藏0
  • python裝飾器詳解

    摘要:為了避免重復調用,可以適當?shù)刈鼍彺?,的裝飾器可以完美的完成這一任務。這意味著我們可以為方法創(chuàng)建裝飾器,只是要記得考慮。裝飾器封裝了函數(shù),這使得調試函數(shù)變得困難。另外,使用裝飾器去管理緩存和權限。 原文地址 之前用python簡單寫了一下斐波那契數(shù)列的遞歸實現(xiàn)(如下),發(fā)現(xiàn)運行速度很慢。 def fib_direct(n): assert n > 0, invalid n ...

    maybe_009 評論0 收藏0

發(fā)表評論

0條評論

Yangyang

|高級講師

TA的文章

閱讀更多
最新活動
閱讀需要支付1元查看
<