1-装饰器
0x-wen

2.装饰器(decorator)

本质函数当作参数传递,利用闭包特性实现

2.1 最原始的装饰器

1
2
3
4
5
6
7
8
9
10
def add(*args):
return sum(args)


# 把函数当做参数,传递给另外一个函数
def new_add(func, *args):
return f"对原函数进行装饰 遵循开放封闭原则: {func(*args)}"


print(new_add(add, 1, 2, 3))

2.2 常见使用方式

编写一个记录日志 和 统计函数执行耗时的装饰器

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
import time


def loger(func):
def wrapper(*args):
print("1 记录日志的代码...")
result = func(*args)
print("2 日志分析的代码...")
return result

return wrapper


# 编写一个计算方法执行耗时的装饰器
def timer(func):
def wrapper(*args, **kwargs):
print("3 计算耗时开始")
start_time = time.time()
result = func(*args)
end_time = time.time()
print(f"{func.__name__}: 耗时: {end_time - start_time}")
print("4 计算耗时结束")
return result

return wrapper


@loger
@timer
def add(*args, **kwargs):
return sum(args)


print(add(11, 1)) # 执行顺序: 1 -> 3 -> func.__name__耗时 -> 4 -> 2 -> func执行结果

2.3 装饰器带参数

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
# 编写一个带参数的装饰器,用于验证用户登录
def login_verify(is_login=False): # 这里接收装饰器的参数
def inner(func): # 接收被装饰的函数
def wrapper(*args, **kwargs): # 这里接收被装饰函数的参数
if is_login: # 装饰器的参数在这里使用,用于判断
print("被装饰函数执行前")
result = func(*args)
print("被装饰函数执行后")
return result
else:
return None

return wrapper # 返回函数的包装器

return inner


@login_verify(is_login=True)
def add(*args, **kwargs):
return sum(args)


print(add(11, 22))

2.4 给类添加一个装饰器

1
2
3
4
5
6
7
8
9
10
11
def class_name(cls):
cls.name = "小明"
return cls

# 给类添加装饰器
@class_name
class A(object):
pass


print(A.name)

2.5 使用类编写装饰器

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
class A:

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

def __call__(self, *args, **kwargs):
print("__call__ is running ...")
return self.func(*args)


@A # 本质 A(add)
def add(*args):
return sum(args)


print(add(1, 2))

2.6 使用类编写装饰器带参数

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
class S:
def __init__(self, func, name):
self.func = func
self.name = name

def __call__(self, *args, **kwargs):
print("类装饰器转入的参数", self.name)
print("1 装饰函数执行之前")
result = self.func(*args)
print("2 装饰函数执行之后")
return result


def add(*args):
return sum(args)


s = S(add, "hello")
print(s(1, 3))
由 Hexo 驱动 & 主题 Keep
总字数 42.8k