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

資訊專(zhuān)欄INFORMATION COLUMN

Python 裝飾器使用指南

NeverSayNever / 600人閱讀

摘要:裝飾器是可調(diào)用的對(duì)象,其參數(shù)是另一個(gè)函數(shù)被裝飾的函數(shù)。第二大特性是,裝飾器在加載模塊時(shí)立即執(zhí)行。另一個(gè)常見(jiàn)的裝飾器是,它的作用是協(xié)助構(gòu)建行為良好的裝飾器。

裝飾器是可調(diào)用的對(duì)象,其參數(shù)是另一個(gè)函數(shù)(被裝飾的函數(shù))。

裝飾器基礎(chǔ)知識(shí)

首先看一下這段代碼

def deco(fn):
    print "I am %s!" % fn.__name__

@deco
def func():
    pass

# output
I am func!

# 沒(méi)有執(zhí)行func 函數(shù) 但是 deco 被執(zhí)行了

在用某個(gè)@decorator來(lái)修飾某個(gè)函數(shù)func時(shí)

@decorator
def func():
    pass

其解釋器會(huì)解釋成下面這樣的語(yǔ)句:

func = decorator(func)

其實(shí)就是把一個(gè)函數(shù)當(dāng)參數(shù)傳到另一個(gè)函數(shù)中,然后再回調(diào),但是值得注意的是裝飾器必須返回一個(gè)函數(shù)給func

裝飾器的一大特性是,能把被裝飾的函數(shù)替換成其他函數(shù)。第二大特性是,裝飾器在加載模塊時(shí)立即執(zhí)行。

裝飾器何時(shí)執(zhí)行

裝飾器的一個(gè)關(guān)鍵特性是,它們?cè)诒谎b飾的函數(shù)定義后立即運(yùn)行。這通常在導(dǎo)入是(python 加載模塊時(shí))。

看下下面的示例:

registry = []  # registry 保存被@register 裝飾的函數(shù)的引用

def register(func):  # register 的參數(shù)是一個(gè)函數(shù)
    print("running register(%s)" % func)  # 打印被裝飾的函數(shù)
    registry.append(func)  # 把 func 存入 `registery`
    return func  # 返回 func:必須返回函數(shù),這里返回的函數(shù)與通過(guò)參數(shù)傳入的一樣

@register  # `f1` 和 `f2`被 `@register` 裝飾
def f1():
    print("running f1()")

@register
def f2():
    print("running f2()")

def f3():  # <7>
    print("running f3()")

def main():  # main 打印 `registry`,然后調(diào)用 f1()、f2()和 f3()
    print("running main()")
    print("registry ->", registry)
    f1()
    f2()
    f3()

if __name__=="__main__":
    main()  # <9>

運(yùn)行代碼結(jié)果如下:

running register()
running register()
running main()
registry -> [, ]
running f1()
running f2()
running f3()

從結(jié)果可以發(fā)現(xiàn)register 在模塊中其他函數(shù)之前運(yùn)行了兩次。調(diào)用 register 時(shí),傳給它的參數(shù)是被裝飾的函數(shù)(例如)。

看完上邊的示例我們知道,函數(shù)被裝飾器裝飾后會(huì)變成裝飾器函數(shù)的一個(gè)參數(shù),那這時(shí)就不得不說(shuō)變量的作用域了。

變量作用域

先看下下邊這段代碼:

def f1(a):
    print(locals())
    print(a)
    print(b)
    
    
f1(3)
# output
{"a": 3}
3
Traceback(most recent call last):
    File "", line 1, in 
    File "", line 3, in f1
NameError: global name "b" is not defined

這里的錯(cuò)誤是因?yàn)槿肿兞?b 沒(méi)有定義,如果我們先在函數(shù)外部給 b 賦值,再調(diào)用這個(gè)方法就不會(huì)報(bào)錯(cuò)了。

函數(shù)運(yùn)行時(shí)會(huì)創(chuàng)建一個(gè)新的作用域(命名空間)。函數(shù)的命名空間隨著函數(shù)調(diào)用開(kāi)始而開(kāi)始,結(jié)束而銷(xiāo)毀。
這個(gè)例子中 f1 的命名空間中只有 {"a": 3},所以 b 會(huì)被認(rèn)為是全局變量。

再看一個(gè)例子:

b = 6
def f2(a):
    print(a)
    print(globals())
    print(locals())
    print(b)
    b = 9
    
f2(3)
# output
3
{
    "__name__": "__main__",
    "__doc__": None, 
    "__package__": None, 
    "__loader__": <_frozen_importlib_external.SourceFileLoader object at 0x10c7f2dd8>, 
    "__spec__": None, 
    "__annotations__": {}, 
    "__builtins__": , 
    "__file__": "~/var_local.py", 
    "__cached__": None, 
    "b": 6, 
    "f2": 
}
{"a": 3}
3
Traceback(most recent call last):
    File "", line 1, in 
    File "", line 3, in f1
UnboundLocalError: local variable "b" referenced before assignment

這個(gè)例子和上一個(gè)例子不同是,我現(xiàn)在函數(shù)外部定義了全局變量b,但是執(zhí)行f2 這個(gè)方法并沒(méi)有打印6,這是為什么呢?
這是因?yàn)閳?zhí)行函數(shù)時(shí) Python 會(huì)嘗試從局部變量中獲取 b,函數(shù)對(duì)于已經(jīng)引用但未賦值的變量并不會(huì)自動(dòng)聲明為局部變量,所以解釋器發(fā)現(xiàn)后邊的賦值之前有引用就會(huì)拋出 UnboundLocalError 錯(cuò)誤。

Python 不要求聲明變量,但是假定在函數(shù)定義體中賦值的變量是局部變量。

如果要讓解釋器把b當(dāng)做全局變量,要使用global聲明:

b = 6
def f3(a):
    global b
    print(a)
    print(b)
    b = 9
    
f2(3)
# output
3
6
閉包

閉包是一種函數(shù),它會(huì)保留定義函數(shù)時(shí)存在的自由變量的綁定,這樣調(diào)用函數(shù)時(shí),雖然定義作用域不可用,但仍能使用那些綁定。

介紹閉包前先要說(shuō)明一下 Python 的函數(shù)參數(shù)

函數(shù)的兩種參數(shù)

函數(shù)有兩種參數(shù)

位置參數(shù)

命名參數(shù)

def foo(x, y=0):
    return x - y
python 中一切都是對(duì)象

函數(shù)和python中其他一樣都是對(duì)象

In [7]: class A(object):
   ...:     pass


In [8]: A
Out[8]: __main__.A
In [9]: type(A)
Out[9]: type
In [10]: def foo():
   ....:     pass


In [11]: type(foo)
Out[11]: function

In [12]: A.__class__
Out[12]: type

In [13]: foo.__class__
Out[13]: function

In [14]: a = 1
In [15]: a.__class__
Out[15]: int

# 類(lèi) 是對(duì)象
In [16]: issubclass(A.__class__, object)
Out[16]: True

# 變量 是對(duì)象
In [17]: issubclass(a.__class__, object)
Out[17]: True

# 函數(shù) 是對(duì)象
In [18]: issubclass(foo.__class__, object)
Out[18]: True

所以函數(shù)也可以作為參數(shù)傳遞給其它函數(shù),也可以被當(dāng)做返回值返回

def add(x, y):
    return x + y

def apply(func):
    return func

>> a = apply(add)
>> type(a)


>> a(1, 2)
>> 3
閉包的使用

先來(lái)看一個(gè)示例:假設(shè)有個(gè)名為 avg 的函數(shù),它的作用是計(jì)算不斷增加的系列值的均值;
它是這么使用的:

>>> avg(10)
10
>>> avg(11)
10.5
>>> avg(12)
11

那么我們考慮下,avg 從何而來(lái),它又在哪里保存歷史值呢,這個(gè)用閉包如何實(shí)現(xiàn)呢?
下邊的代碼是閉包的實(shí)現(xiàn):

def make_averager():
    series = []

    def averager(new_value):
        series.append(new_value)
        total = sum(series)
        return total/len(series)

    return averager

調(diào)用 make_averager 時(shí),返回一個(gè) averager 函數(shù)對(duì)象。每次調(diào)用 averager 時(shí),它都會(huì)把參數(shù)添加到系列值中,然后計(jì)算當(dāng)前平均值。

avg = make_averager()

>>> avg(10)
10
>>> avg(11)
10.5
>>> avg(12)
11

seriesmake_averager 函數(shù)的局部變量,因?yàn)槟莻€(gè)函數(shù)的定義體中初始化了series: series=[]。但在averager 函數(shù)中,series 是自由變量(指未在本地作用域中綁定的變量)。

averager 的閉包延伸到那個(gè)函數(shù)的作用域之外,包含自由變量series的綁定。

avg 就是一個(gè)閉包

也可以說(shuō) make_averager 指向一個(gè)閉包

或者說(shuō) make_averager 是閉包的工廠函數(shù)

閉包可以認(rèn)為是一個(gè)內(nèi)層函數(shù)(averager),由一個(gè)變量指代,而這個(gè)變量相對(duì)于外層包含它的函數(shù)而言,是本地變量
嵌套定義在非全局作用域里面的函數(shù)能夠記住它在被定義的時(shí)候它所處的封閉命名空間

閉包 只是在形式和表現(xiàn)上像函數(shù),但實(shí)際上不是函數(shù)。函數(shù)是一些可執(zhí)行的代碼,這些代碼在函數(shù)被定義后就確定了,不會(huì)在執(zhí)行時(shí)發(fā)生變化,所以一個(gè)函數(shù)只有一個(gè)實(shí)例。閉包在運(yùn)行時(shí)可以有多個(gè)實(shí)例,不同的引用環(huán)境和相同的函數(shù)組合可以產(chǎn)生不同的實(shí)例。

裝飾器 實(shí)現(xiàn)一個(gè)簡(jiǎn)單的裝飾器

對(duì)一個(gè)已有的模塊做一些“修飾工作”,所謂修飾工作就是想給現(xiàn)有的模塊加上一些小裝飾(一些小功能,這些小功能可能好多模塊都會(huì)用到),但又不讓這個(gè)小裝飾(小功能)侵入到原有的模塊中的代碼里去

def my_decorator(func):
    def wrapper():
        print "Before the function runs"
        func() # 這行代碼可用,是因?yàn)?wrapper 的閉包中包含自由變量 func
        print "After the function runs"
    return wrapper

def my_func():
    print "I am a stand alone function"


>> my_func()

# output
I am a stand alone function

# 然后,我們?cè)谶@里裝飾這個(gè)函數(shù)
# 將函數(shù)傳遞給裝飾器,裝飾器將動(dòng)態(tài)地將其包裝在任何想執(zhí)行的代碼中,然后返回一個(gè)新的函數(shù)

>> my_func = my_decorator(my_func)
>> my_func()
#output
Before the function runs
I am a stand alone function
After the function runs

# 也可以這么寫(xiě)

@ my_decorator
def my_func():
    print "I am a stand alone function"

>> my_func()
#output
Before the function runs
I am a stand alone function
After the function runs

裝飾器是設(shè)計(jì)模式中裝飾器模式(英文版)的python實(shí)現(xiàn)。

多個(gè)裝飾器

裝飾器可以嵌套使用

def bread(func):
    def wrapper():
        print ""
        func()
        print "<\______/>"
    return wrapper

def ingredients(func):
    def wrapper():
        print "#tomatoes#"
        func()
        print "~salad~"
    return wrapper

def sandwich(food="--ham--"):
    print food

#### outputs:
嵌套兩個(gè)裝飾器
>> sandwich = bread(ingredients(sandwich))
>> sandwich()

#### outputs

 #tomatoes#
 --ham--
 ~salad~
<\______/>

更簡(jiǎn)單的寫(xiě)法

@bread
@ingredients
def sandwich(food="--ham--"):
    print food

裝飾器的順序是很重要的

如果我們換下順序就會(huì)發(fā)現(xiàn),三明治變成了披薩。。

@ingredients
@bread
def sandwich(food="--ham--"):
    print food

# outputs:
    
 #tomatoes#
 
   --ham--
 <\______/>
 ~salad~
Decorator 的工作原理

首先看一下這段代碼

def deco(fn):
    print "I am %s!" % fn.__name__

@deco
def func():
    pass

# output
I am func!

# 沒(méi)有執(zhí)行func 函數(shù) 但是 deco 被執(zhí)行了

在用某個(gè)@decorator來(lái)修飾某個(gè)函數(shù)func時(shí)

@decorator
def func():
    pass

其解釋器會(huì)解釋成下面這樣的語(yǔ)句:

func = decorator(func)

其實(shí)就是把一個(gè)函數(shù)當(dāng)參數(shù)傳到另一個(gè)函數(shù)中,然后再回調(diào)
但是值得注意的是裝飾器必須返回一個(gè)函數(shù)給func

回到剛才的例子

def my_decorator(func):
    def wrapper():
        print "Before the function runs"
        func()
        print "After the function runs"
    return wrapper

def my_func():
    print "I am a stand alone function"

>> my_func = my_decorator(my_func)
>> my_func()
#output
Before the function runs
I am a stand alone function
After the function runs

my_decorator(my_func)返回了wrapper()函數(shù),所以,my_func其實(shí)變成了wrapper的一個(gè)變量,而后面的my_func()執(zhí)行其實(shí)變成了wrapper()

比如:多個(gè)decorator

@decorator_one
@decorator_two
def func():
    pass

相當(dāng)于:

func = decorator_one(decorator_two(func))

比如:帶參數(shù)的decorator:

@decorator(arg1, arg2)
def func():
    pass
# 相當(dāng)于:

func = decorator(arg1,arg2)(func)
帶參數(shù)的裝飾器

首先看一下, 如果被裝飾的方法有參數(shù)

def a_decorator(method_to_decorate):
    def wrapper(self, x):
        x -= 3
        print "x is %s" % x
        method_to_decorate(self, x)
    return wrapper


class A(object):

    def __init__(self):
        self.b = 42

    @a_decorator
    def number(self, x):
        print "b is %s" % (self.b + x)


a = A()
a.number(-3)

# output
x is -6
b is 36

通常我們都使用更加通用的裝飾器,可以作用在任何函數(shù)或?qū)ο蠓椒ㄉ?,而不必關(guān)心其參數(shù)使用

def a_decorator(method_to_decorate):
    def wrapper(*args, **kwargs):
        print "****** args ******"
        print args
        print kwargs
        method_to_decorate(*args, **kwargs)
    return wrapper

@a_decorator
def func():
    pass

func()
#output
****** args ******
()
{}

@a_decorator
def func_with_args(a, b=0):
    pass
    return a + b

func_with_args(1, b=2)

#output
****** args ******
(1,)
{"b": 2}

上邊的示例是帶參數(shù)的被裝飾函數(shù)

現(xiàn)在我們看一下向裝飾器本身傳遞參數(shù)

向裝飾器本身傳遞參數(shù)

裝飾器必須使用函數(shù)作為參數(shù),你不能直接傳遞參數(shù)給裝飾器本身
如果想傳遞參數(shù)給裝飾器,可以 聲明一個(gè)用于創(chuàng)建裝飾器的函數(shù)

# 我是一個(gè)創(chuàng)建裝飾器的函數(shù)
def decorator_maker():
    print "I make decorators!"

    def my_decorator(func):
        print "I am a decorator!"

        def wrapped():
            print "I am the wrapper around the decorated function. "
            return func()

        print "As the decorator, I return the wrapped function."
        return wrapped

    print "As a decorator maker, I return a decorator"
    return my_decorator

# decorator_maker()返回的是一個(gè)裝飾器
new_deco = decorator_maker()

#outputs
I make decorators!
As a decorator maker, I return a decorator

# 使用裝飾器
def decorated_function():
    print "I am the decorated function"

decorated_function = new_deco(decorated_function)   
decorated_function()

# outputs
I make decorators!
As a decorator maker, I return a decorator
I am a decorator!
As the decorator, I return the wrapped function.
I am the wrapper around the decorated function.
I am the decorated  function

使用@修飾

decorated_function = new_deco(decorated_function)

# 等價(jià)于下面的方法

@new_deco
def func():
    print "I am the decorated function"


@decorator_maker()
def func():
    print "I am the decorated function"

my_decorator(裝飾器函數(shù))是decorator_maker(裝飾器生成函數(shù))的內(nèi)部函數(shù)

所以可以使用把參數(shù)加在decorator_maker(裝飾器生成函數(shù))的方法像裝飾器傳遞參數(shù)

# 我是一個(gè)創(chuàng)建帶參數(shù)裝飾器的函數(shù)
def decorator_maker_with_arguments(darg1, darg2):
    print "I make decorators! And I accept arguments:", darg1, darg2

    def my_decorator(func):
        print "I am a decorator! Somehow you passed me arguments:", darg1, darg2

        def wrapped(farg1, farg2):
            print "I am the wrapper around the decorated function."
            print "I can access all the variables", darg1, darg2, farg1, farg2
            return func(farg1, farg2)

        print "As the decorator, I return the wrapped function."
        return wrapped

    print "As a decorator maker, I return a decorator"
    return my_decorator

@decorator_maker_with_arguments("deco_arg1", "deco_arg2")
def decorated_function_with_arguments(function_arg1, function_arg2):
    print ("I am the decorated function and only knows about my arguments: {0}"
           " {1}".format(function_arg1, function_arg2))


decorated_function_with_arguments("farg1", "farg2")

# outputs

I make decorators! And I accept arguments: deco_arg1 deco_arg2
As a decorator maker, I return a decorator
I am a decorator! Somehow you passed me arguments: deco_arg1 deco_arg2
As the decorator, I return the wrapped function.
I am the wrapper around the decorated function.
I can access all the variables deco_arg1 deco_arg2 farg1 farg2
I am the decorated function and only knows about my arguments: farg1 farg2    

這里裝飾器生成函數(shù)內(nèi)部傳遞參數(shù)是閉包的特性

使用裝飾器需要注意

裝飾器是Python2.4的新特性

裝飾器會(huì)降低代碼的性能

裝飾器僅在Python代碼導(dǎo)入時(shí)被調(diào)用一次,之后你不能動(dòng)態(tài)地改變參數(shù).當(dāng)你使用"import x",函數(shù)已經(jīng)被裝飾

使用 functools.wraps

最后Python2.5解決了最后一個(gè)問(wèn)題,它提供functools模塊,包含functools.wraps,這個(gè)函數(shù)會(huì)將被裝飾函數(shù)的名稱(chēng)、模塊、文檔字符串拷貝給封裝函數(shù)

def foo():
    print "foo"

print foo.__name__
#outputs: foo

# 但當(dāng)你使用裝飾器
def bar(func):
    def wrapper():
        print "bar"
        return func()
    return wrapper

@bar
def foo():
    print "foo"

print foo.__name__
#outputs: wrapper

"functools" 可以修正這個(gè)錯(cuò)誤

import functools

def bar(func):
    # 我們所說(shuō)的 "wrapper", 封裝 "func"
    @functools.wraps(func)
    def wrapper():
        print "bar"
        return func()
    return wrapper

@bar
def foo():
    print "foo"

# 得到的是原始的名稱(chēng), 而不是封裝器的名稱(chēng)
print foo.__name__
#outputs: foo
類(lèi)裝飾器
class myDecorator(object):

    def __init__(self, func):
        print "inside myDecorator.__init__()"
        self.func = func

    def __call__(self):
        self.func()
        print "inside myDecorator.__call__()"

@myDecorator
def aFunction():
    print "inside aFunction()"

print "Finished decorating aFunction()"

aFunction()

# output:
# inside myDecorator.__init__()
# Finished decorating aFunction()
# inside aFunction()
# inside myDecorator.__call__()

我們可以看到這個(gè)類(lèi)中有兩個(gè)成員:

一個(gè)是__init__(),這個(gè)方法是在我們給某個(gè)函數(shù)decorator時(shí)被調(diào)用,所以,需要有一個(gè)func的參數(shù),也就是被decorator的函數(shù)。

一個(gè)是__call__(),這個(gè)方法是在我們調(diào)用被decorator函數(shù)時(shí)被調(diào)用的

如果decorator有參數(shù)的話,__init__() 就不能傳入func了,而fn是在__call__的時(shí)候傳入

class myDecorator(object):

    def __init__(self, arg1, arg2):
        self.arg1 = arg2

    def __call__(self, func):
        def wrapped(*args, **kwargs):
            return self.func(*args, **kwargs)
        return wrapped
裝飾器示例

Python 內(nèi)置了三個(gè)用于裝飾方法的函數(shù):property、classmethod和 staticmethod。
另一個(gè)常見(jiàn)的裝飾器是 functools.wraps,它的作用是協(xié)助構(gòu)建行為良好的裝飾器。

functools.lru_cache

functools.lru_cache 實(shí)現(xiàn)了內(nèi)存緩存功能,它可以把耗時(shí)長(zhǎng)的函數(shù)結(jié)果保存起來(lái),避免傳入相同參數(shù)時(shí)重復(fù)計(jì)算。

我們自己的實(shí)現(xiàn)代碼如下:

from functools import wraps
def memo(fn):
    cache = {}
    miss = object()

    @wraps(fn)
    def wrapper(*args):
        result = cache.get(args, miss)
        if result is miss:
            result = fn(*args)
            print "{0} has been used: {1}x".format(fn.__name__, wrapper.count)
            cache[args] = result
        return result

    return wrapper

@memo
def fib(n):
    if n < 2:
        return n
    return fib(n - 1) + fib(n - 2)
統(tǒng)計(jì)函數(shù)執(zhí)行次數(shù)的裝飾器
def counter(func):
    """
    記錄并打印一個(gè)函數(shù)的執(zhí)行次數(shù)
    """
    def wrapper(*args, **kwargs):
        wrapper.count = wrapper.count + 1
        res = func(*args, **kwargs)
        print "{0} has been used: {1}x".format(func.__name__, wrapper.count)
        return res
    wrapper.count = 0
    return wrapper

裝飾器做緩存

帶有過(guò)期時(shí)間的內(nèi)存緩存
def cache_for(duration):
    def deco(func):
        @wraps(func)
        def fn(*args, **kwargs):
            key = pickle.dumps((args, kwargs))
            value, expire = func.func_dict.get(key, (None, None))
            now = int(time.time())
            if value is not None and expire > now:
                return value
            value = func(*args, **kwargs)
            func.func_dict[key] = (value, int(time.time()) + duration)
            return value
        return fn
    return deco
統(tǒng)計(jì)代碼運(yùn)行時(shí)間
def timeit(fn):

    @wraps(fn)
    def real_fn(*args, **kwargs):
        if config.common["ENVIRON"] == "PRODUCTION":
            return fn(*args, **kwargs)

        _start = time.time()
        #app.logger.debug("Start timeit for %s" % fn.__name__)
        result = fn(*args, **kwargs)
        _end = time.time()
        _last = _end - _start
        app.logger.debug("End timeit for %s in %s seconds." %
                         (fn.__name__, _last))
        return result

    return real_fn
參考鏈接

How can I make a chain of function decorators in Python?

理解PYTHON中的裝飾器

Python修飾器的函數(shù)式編程

Understanding Python Decorators in 12 Easy Steps!

PEP 0318 -- Decorators for Functions and Methods

PEP 3129 -- Class Decorators

[args and *kwargs? [duplicate]](http://stackoverflow.com/ques...

why-cant-i-set-a-global-variable-in-python

【flask route】

PythonDecoratorLibrary

關(guān)于Python Decroator的各種提案


最后,感謝女朋友支持。

歡迎關(guān)注(April_Louisa) 請(qǐng)我喝芬達(dá)

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

轉(zhuǎn)載請(qǐng)注明本文地址:http://systransis.cn/yun/40745.html

相關(guān)文章

  • Python】一文弄懂python裝飾(附源碼例子)

    摘要:裝飾器的使用符合了面向?qū)ο缶幊痰拈_(kāi)放封閉原則。三簡(jiǎn)單的裝飾器基于上面的函數(shù)執(zhí)行時(shí)間的需求,我們就手寫(xiě)一個(gè)簡(jiǎn)單的裝飾器進(jìn)行實(shí)現(xiàn)。函數(shù)體就是要實(shí)現(xiàn)裝飾器的內(nèi)容。類(lèi)裝飾器的實(shí)現(xiàn)是調(diào)用了類(lèi)里面的函數(shù)。類(lèi)裝飾器的寫(xiě)法比我們裝飾器函數(shù)的寫(xiě)法更加簡(jiǎn)單。 目錄 前言 一、什么是裝飾器 二、為什么要用裝飾器 ...

    liuchengxu 評(píng)論0 收藏0
  • Python: 會(huì)打扮的裝飾

    摘要:一般情況下,我們使用裝飾器提供的語(yǔ)法糖,來(lái)簡(jiǎn)化上面的寫(xiě)法像上面的情況,可以動(dòng)態(tài)修改函數(shù)或類(lèi)功能的函數(shù)就是裝飾器。本文標(biāo)題為會(huì)打扮的裝飾器本文鏈接為參考資料修飾器的函數(shù)式編程中的裝飾器介紹思誠(chéng)之道裝飾器入門(mén)與提高賴(lài)明星 裝飾器 我們知道,在 Python 中,我們可以像使用變量一樣使用函數(shù): 函數(shù)可以被賦值給其他變量 函數(shù)可以被刪除 可以在函數(shù)里面再定義函數(shù) 函數(shù)可以作為參數(shù)傳遞給另外...

    blastz 評(píng)論0 收藏0
  • Python學(xué)習(xí)之路26-函數(shù)裝飾和閉包

    摘要:初步認(rèn)識(shí)裝飾器函數(shù)裝飾器用于在源代碼中標(biāo)記函數(shù),以某種方式增強(qiáng)函數(shù)的行為。函數(shù)裝飾器在導(dǎo)入模塊時(shí)立即執(zhí)行,而被裝飾的函數(shù)只在明確調(diào)用時(shí)運(yùn)行。只有涉及嵌套函數(shù)時(shí)才有閉包問(wèn)題。如果想保留函數(shù)原本的屬性,可以使用標(biāo)準(zhǔn)庫(kù)中的裝飾器。 《流暢的Python》筆記本篇將從最簡(jiǎn)單的裝飾器開(kāi)始,逐漸深入到閉包的概念,然后實(shí)現(xiàn)參數(shù)化裝飾器,最后介紹標(biāo)準(zhǔn)庫(kù)中常用的裝飾器。 1. 初步認(rèn)識(shí)裝飾器 函數(shù)裝飾...

    sunny5541 評(píng)論0 收藏0
  • Python裝飾

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

    aisuhua 評(píng)論0 收藏0
  • Python中的函數(shù)裝飾和閉包

    摘要:變量查找規(guī)則在中一個(gè)變量的查找順序是局部環(huán)境,閉包,全局,內(nèi)建閉包引用了自由變量的函數(shù)。閉包的作用閉包的最大特點(diǎn)是可以將父函數(shù)的變量與內(nèi)部函數(shù)綁定,并返回綁定變量后的函數(shù),此時(shí)即便生成閉包的環(huán)境父函數(shù)已經(jīng)釋放,閉包仍然存在。 導(dǎo)語(yǔ):本文章記錄了本人在學(xué)習(xí)Python基礎(chǔ)之函數(shù)篇的重點(diǎn)知識(shí)及個(gè)人心得,打算入門(mén)Python的朋友們可以來(lái)一起學(xué)習(xí)并交流。 本文重點(diǎn): 1、掌握裝飾器的本質(zhì)、功...

    caozhijian 評(píng)論0 收藏0
  • python裝飾的原理和使用

    摘要:我們以測(cè)量函數(shù)運(yùn)行時(shí)間為例來(lái)講一講裝飾器的運(yùn)行原理。三更加通用的裝飾器前面兩部分講了裝飾器的原理,這一部分就講講要寫(xiě)出一個(gè)通用的裝飾器需要注意的問(wèn)題。首先就是參數(shù)的問(wèn)題,裝飾器返回的函數(shù)不是原來(lái)的函數(shù),函數(shù)的簽名也就和原來(lái)的函數(shù)簽名不一樣。 一、最簡(jiǎn)單的裝飾器 裝飾器是python中很基礎(chǔ)也很實(shí)用的一個(gè)特性。通過(guò)裝飾器我們可以很方便地為一些函數(shù)添加相同的功能。我們以測(cè)量函數(shù)運(yùn)行時(shí)間為例...

    goji 評(píng)論0 收藏0

發(fā)表評(píng)論

0條評(píng)論

最新活動(dòng)
閱讀需要支付1元查看
<