Python装饰器案例

Python装饰器

当我们谈论 Python 中的装饰器时,我们实际上是在讨论一种高级函数。装饰器允许开发人员动态地修改函数或类的行为,而无需直接修改它们的代码。这种特性使得装饰器在许多常见的编程场景中非常有用,比如日志记录、性能测试、权限验证等。
Python装饰器是一种强大的功能,它允许您动态地修改类或函数的行为。为了深入了解装饰器,我们需要先了解闭包。

  1. 闭包

闭包是指在函数中再嵌套一个函数,并且内部函数引用了外部函数的变量。例如:

def outer(x):
    def inner(y):
        return x + y
    return inner

print(outer(2)(3))
# 输出:5

在这个示例中,outer 函数内部定义了 inner 函数,并且 inner 函数引用了外部函数 outer 的变量 x。因此,outer(6)(5) 返回 2 + 3 的结果。

  1. 装饰器

装饰器实际上就是一种闭包的应用。它是一个用于扩展原函数功能的函数,而且其返回值也是一个函数。通过使用装饰器,可以在不修改原函数代码的情况下给函数增加新的功能。例如:

def debug(func):
    def wrapper():
        print("[DEBUG]: enter {}()".format(func.__name__))
        return func()
    return wrapper

@debug
def hello():
    print("hello")

hello()
# 输出:
# [DEBUG]: enter hello()
# hello

在这个例子中,装饰器 debug 给函数 hello 加上了进入函数的debug模式,而无需修改原函数的代码。

  1. 带参数的装饰器

装饰器也可以接受参数,装饰的函数也可以传递参数。例如:

def logging(level):
    def outwrapper(func):
        def wrapper(*args, **kwargs):
            print("[{0}]: enter {1}()".format(level, func.__name__))
            return func(*args, **kwargs)
        return wrapper
    return outwrapper

@logging(level="INFO")
def hello(a, b, c):
    print(a, b, c)

hello("hello,","good","morning")
# 输出:
# [INFO]: enter hello()
# hello, good morning

在这个示例中,装饰器 logging 接受一个参数 level,然后返回一个完整的装饰器。同时被装饰的函数 hello 也传递了三个参数。

  1. 类装饰器
    除了函数装饰器外,还可以使用类来实现装饰器。类装饰器的使用方法与函数装饰器类似,其实质是使用了类方法中的 __call__ 魔法方法来实现类的直接调用。例如:
class logging(object):
    def __init__(self, func):
        self.func = func

    def __call__(self, *args, **kwargs):
        print("[DEBUG]: enter {}()".format(self.func.__name__))
        return self.func(*args, **kwargs)

@logging
def hello(a, b, c):
    print(a, b, c)

hello("hello,","good","morning")
# 输出:
# [DEBUG]: enter hello()
# hello, good morning

类装饰器也可以带参数,例如:

class logging(object):
    def __init__(self, level):
        self.level = level

    def __call__(self, func):
        def wrapper(*args, **kwargs):
            print("[{0}]: enter {1}()".format(self.level, func.__name__))
            return func(*args, **kwargs)
        return wrapper

@logging(level="TEST")
def hello(a, b, c):
    print(a, b, c)

hello("hello,","good","morning")
# 输出:
# [TEST]: enter hello()
# hello, good morning
  1. 使用案例

在这个例子中,my_timer 装饰器函数添加了计时功能,会在执行函数时输出函数的执行时间。

import time

def my_timer(original_function):
    def wrapper(*args, **kwargs):
        t1 = time.time()
        result = original_function(*args, **kwargs)
        t2 = time.time() - t1
        print('{} ran in: {} sec'.format(original_function.__name__, t2))
        return result

    return wrapper

@my_timer
def display_info(name, age):
    time.sleep(1)
    print('display_info ran with arguments ({}, {})'.format(name, age))

display_info('Fiang', 22)
  1. 总结
    Python 装饰器为我们提供了一种轻便且灵活的方式来通过对函数进行修饰,添加额外的功能,而无需修改原始函数的代码。装饰器是 Python 中一个强大且常用的特性,值得我们深入学习和掌握。

你可能感兴趣的:(python,python,开发语言)