Python 装饰器

时间:2022-11-09 21:55:34

闭包

理解装饰器之前需要先了解一下闭包。闭包即嵌套函数,外部函数将内部函数返回。在外部执行。

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


print(outer(6)(6))
# 在调用 outer返回 inter。执行inter

函数装饰器

def outer(func):
    def inner(*args, **kwargs):
        print(args)
        return func(*args, **kwargs)

    return inner


@outer
def test(a, b):
    print('test')
('2', 1)
  • 调用 test 函数 @outer 将test作为参数传递给 outer 函数

  • outer 函数 将 inner 函数返回。此时,调用 test 可以看做调用 inter 函数。

  • return func(*args, **kwargs) 返回的是 test 函数本身

  • 所以在 return func 之前可以增加一些额外的逻辑--装饰器的妙用

装饰器增加额外参数

def check_permission(code):
    def wrapper(func):
        def inner(*args, **kwargs):
            ret = func(*args, **kwargs)
            return ret

        return inner

    return wrapper

在 web 场景中 需要效验权限。那么可以在 check_permission 传入权限唯一标识。通过code 值去判定权限。

格式化装饰函数参数

在开发过程中,你所装饰的函数可能函数不统一。可以在装饰器中增加装饰器,修改参数传入方式

# 格式化装饰器

# 格式参数不需要额外参数 两层即可
def content(f):
    def wrapper(func):
        def inner(*args, **kwargs):
            info = next(arg for arg in args if isinstance(arg, int))
            return func(info, *args, **kwargs)

        return inner

    return wrapper

# 权限效验装饰器
def check_permission(code):
    def wrapper(func):
        @content('a')
        def inner(info, *args, **kwargs):
            # info 为统一后的参数
            print(info, 'info')
            ret = func(*args, **kwargs)

            return ret

        return inner

    return wrapper

以上是一个项目中遇到的问题。

类装饰器

个人喜欢类装饰器

class CheckPermission:

    def __init__(self, a, b):
        self.a = a
        self.b = b

    def __call__(self, func):
        def wrapper(*args, **kwargs):
            # 可以使用 参数 
            return func(*args, **kwargs)

        return wrapper


@CheckPermission(1, 2)
def test(a, b):
    print('test')

[参照链接](python 装饰器详解 - 知乎 (zhihu.com)) 还有一些自己的新的想法。

下个 增加一些 functools import wraps 内容。未完待续...