【python】装饰器(1)

一、介绍

装饰器(Decorators)是 Python 的一个重要部分。

Python装饰器可扩展和修改可调用对象的行为,而无需修改可调用对象本身。装饰器是装饰(或包装)其他功能并在包装的功能运行之前和之后执行代码的功能。让我们的代码更简短。

Python装饰器通常用于日志记录,性能测试,身份验证和授权,计时和缓存等。

python官网:链接
python教程:链接
Decorators:链接

二、装饰器用法

python提供了@符号作为装饰器的语法糖,使我们更方便的应用装饰函数。但使用语法糖要求装饰函数必须return一个函数对象。

2.1.不带@符号的Python装饰器
def a(func):
    def wrapper():
        print("11111")
        func()
        print("22222")
    return wrapper
    
def b():
    print("bbbbbbb")
    
#调用
func = a(b)
func()

这里a函数是一个装饰器,通过在输出中添加两行打印来装饰
在这里插入图片描述

2.2.带@符号的Python装饰器
def a(func):
    def wrapper():
        print("11111")
        func()
        print("22222")
    return wrapper
    
@a
def b():
    print("bbbbbbb")
    
#调用
b()

在这里插入图片描述

2. functools @wraps装饰器

应用装饰功能后,namedoc,和__module__原有功能的属性都将丢失。这使调试很麻烦。为了解决这个问题,我们可以使用functool’s @wraps装饰器。

#!/usr/bin/env python

from functools import wraps

def a(fun):
    @wraps(fun)
    def wrapper():
        '''this is wrapper()''' 
        print("***************************")
        fun()
        print("***************************")
    return wrapper

@a
def b():
    '''this is b()''' 
    print("bbbb")
    
#调用
b()
print(b.__name__)
print(b.__doc__)

在这里插入图片描述

2.Python类装饰器

我们调用该update_wrapper()函数。它具有与@wraps装饰器相同的目的;即,它保留原始函数(name__或__doc)的元数据。我们保留对原始函数的引用并设置num_of_calls变量。

使用装饰器实现一个计数器功能

#!/usr/bin/env python

import functools

class CountCalls:

    def __init__(self, fun):

        functools.update_wrapper(self, fun)
        self.fun = fun
        self.num_of_calls = 0

    def __call__(self, *args, **kwargs):

        self.num_of_calls += 1
        print(f"Call {self.num_of_calls} of {self.fun.__name__} fun")
        return self.fun(*args, **kwargs)

@CountCalls
def hello():
    print("Hello there!")

#调用
a = hello()
b = hello
print(b.num_of_calls)

在这里插入图片描述


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值