装饰器

1.装饰器的简约版本

 1 # 统计函数的执行时间
 2 import time
 3 
 4 
 5 def index():
 6     time.sleep(2)
 7     print('from index')
 8 
 9 
10 def home():
11     time.sleep(3)
12     print('from home')
13 
14 def outer(func):
15     # func = index
16 
17     def get_time():
18         # 1. 统计一下函数执行前的时间戳
19         start_time = time.time()
20         func()
21 
22         # 2. 统计一下函数执行完之后的时间戳
23         end_time = time.time()
24 
25         # 3. 计算差值
26         print('函数执行时间:%s' % (end_time - start_time))
27 
28     return get_time
29 
30 
31 index = outer(index)  # res=>get_time的内存地址
32 index()  # get_time()

 

2.装饰器的进阶版本

def outer(func):
    # func = index

    def get_time(*args, **kwargs):
        # 1. 统计一下函数执行前的时间戳
        start_time = time.time()
        func(*args, **kwargs)  # login()

        # 2. 统计一下函数执行完之后的时间戳
        end_time = time.time()

        # 3. 计算差值
        print('函数执行时间:%s' % (end_time - start_time))

    return get_time


login = outer(login)  # res=>get_time的内存地址
login('ly')  # get_time()

index=outer(index)
index()

装饰器进阶版本(解决了函数传参问题)

 
 1 def outer(func):
 2     # func = index
 3 
 4     def get_time(*args, **kwargs):
 5         # 1. 统计一下函数执行前的时间戳
 6         start_time = time.time()
 7         func(*args, **kwargs)  # login()
 8 
 9         # 2. 统计一下函数执行完之后的时间戳
10         end_time = time.time()
11 
12         # 3. 计算差值
13         print('函数执行时间:%s' % (end_time - start_time))
14 
15     return get_time
16 
17 
18 login = outer(login)  # res=>get_time的内存地址
19 login('ly')  # get_time()
20 
21 index=outer(index)

解决函数返回值问题

def login(name):
    time.sleep(1)
    print('from home', name)
    return 'from login'

def outer(func):
    # func = index

    def get_time(*args, **kwargs):
        # 1. 统计一下函数执行前的时间戳
        start_time = time.time()
        res=func(*args, **kwargs)  # login()

        # 2. 统计一下函数执行完之后的时间戳
        end_time = time.time()

        # 3. 计算差值
        print('函数执行时间:%s' % (end_time - start_time))
        return res
    return get_time


login = outer(login)  # res=>get_time的内存地址
res=login('ly')  # get_time()
print(res)

 

3.装饰器的练习题

 1 # 调用index函数,调用之前,需要输入用户名和密码,并且,用户名和密码必须输入正确
 2 
 3 def home():
 4     print('from home')
 5 
 6 
 7 def login():
 8     print('from login')
 9 
10 
11 is_auth = {'is_login': False}
12 
13 
14 def login_auth(func):
15     # func = index
16     def auth():
17         # 判断是否已经认证成功了
18         if is_auth.get('username'):
19             res = func()
20             return res
21         # 1. 让用户输入用户名和密码
22         username = input('username:').strip()
23         password = input('password:').strip()
24 
25         # 2. 判断用户名和密码
26         if username == 'ly' and password == '123':
27             func()
28             is_auth['is_login'] = True
29         else:
30             print('输入错误,不能调用函数')
31 
32     return auth  # 一定别忘记把内层函数的函数名返回出去
33 
34 
35 # auth(index)
36 # auth(home)
37 index = login_auth(index)  # res => auth
38 index()  # auth()
39 
40 home = login_auth(home)
41 home()
42 
43 login = login_auth(login)
44 login()

 

4.装饰器的固定模板

1 def outer(func):
2     def inner():
3         print('函数执行之前要执行的代码')
4         res = func()
5         print('函数执行之后要执行的代码')
6         return res
7 
8     return inner

 

5.装饰器的语法糖

def outer(func):
    def inner():
        start_time = time.time()
        res = func()
        end_time = time.time()
        print('函数执行时间:%s' % (end_time - start_time))
        return res

    return inner


# 统计函数的执行时间
@outer  # # index = outer(index)
def index():
    time.sleep(3)
    print('from index')

index()
'''
    装饰器语法糖的执行流程:
        把语法糖下面紧贴着的函数名当成参数传递给装饰器函数参数
'''


@outer  # home = outer(home)
def home():
    print('from home')

home()

装饰器双层语法糖

# 统计函数执行时间的装饰器
import time


def get_time(func):
    def inner():
        start_time = time.time()
        res = func()
        end_time = time.time()
        print('函数执行时间:%s' % (end_time - start_time))
        return res

    return inner


# 认证装饰器
def login_auth(func):
    # func = index
    def auth():
        # 1. 让用户输入用户名和密码
        username = input('username:').strip()
        password = input('password:').strip()

        # 2. 判断用户名和密码
        if username == 'ly' and password == '123':
            func()  # inner()
        else:
            print('输入错误,不能调用函数')

    return auth  # 一定别忘记把内层函数的函数名返回出去


@login_auth # index=login_auth(inner)  #index=>auth的内存地址
@get_time  # inner=get_time(index)
def index(): # def auth()
    time.sleep(2)
    print('from index')


index()  # auth()

 

6.有参装饰器

 1 # 认证装饰器
 2 def outter(source_data, a, b,c):
 3     # source_data = 'file'
 4     def login_auth(func):
 5         # func = index
 6         def auth( *args, **kwargs):
 7             # 1. 让用户输入用户名和密码
 8             # username = input('username:').strip()
 9             # password = input('password:').strip()
10             if source_data == 'file':
11                 print('从文件中读数据')
12             elif source_data =='mysql':
13                 print('从mysql中读取数据')
14             elif source_data == 'oracle':
15                 print('从oracle中读取数据')
16 
17 
18         return auth  # 一定别忘记把内层函数的函数名返回出去
19     return login_auth
20 @outter('file', 1, 2,3)  # outter('file')    @login_auth
21 def index():
22     pass
23 index()

 

上一篇:keepalived配置高可用


下一篇:Django学习笔记-1