装饰器:本质就是函数,功能是为其他函数添加附加功能
原则:
a.不修改被修饰函数的源代码
b.不修改被修饰函数的调用方式
公式:
装饰器=高阶函数+函数嵌套+闭包
高阶函数的定义:
a.函数接收的参数是一个函数名
b.函数的返回值是一个函数名
c.满足上述条件任意一个,都可称之为高阶函数

1 #!/usr/bin/env python
2 # -*- coding:utf-8 -*-
3
4
5 def foo():
6 print('你好呀!')
7
8
9 def test(func):
10 func()
11
12
13 test(foo)
高阶函数条件一示例

1 #!/usr/bin/env python
2 # -*- coding:utf-8 -*-
3
4
5 def father(name):
6 print('from father %s' %name)
7
8 def son():
9 print('from son')
10
11 def grandson():
12 print('from grandson')
13 grandson()
14 son()
15
16
17 father('alex')
函数嵌套

1 #!/usr/bin/env python
2 # -*- coding:utf-8 -*-
3 import time
4
5
6 def timmer(func):
7 def wrapper():
8 start_time = time.time()
9 func()
10 stop_time = time.time()
11 print('函数运行时间 %s' % (stop_time - start_time))
12
13 return wrapper
14
15
16 @timmer # 第一种调用方式;@timmer 相当于 test = timmer(test)
17 def test():
18 time.sleep(3)
19 print('test函数运行完毕')
20
21
22 # test = timmer(test) # 第二种调用方式
23 # test()
24
25 test()
装饰器的实现

1 #!/usr/bin/env python
2 # -*- coding:utf-8 -*-
3 import time
4
5
6 def timmer(func):
7 def wrapper():
8 start_time = time.time()
9 res = func()
10 stop_time = time.time()
11 print('函数运行时间 %s' % (stop_time - start_time))
12 return res
13 return wrapper
14
15
16 @timmer # 第一种调用方式;@timmer 相当于 test = timmer(test)
17 def test():
18 time.sleep(3)
19 print('test函数运行完毕')
20 return '这是test的返回值'
21
22
23 res = test()
24 print(res)
装饰器加上返回值

1 #!/usr/bin/env python
2 # -*- coding:utf-8 -*-
3 import time
4
5
6 def timmer(func):
7 def wrapper(name, age):
8 start_time = time.time()
9 res = func(name, age)
10 stop_time = time.time()
11 print('函数运行时间 %s' % (stop_time - start_time))
12 return res
13 return wrapper
14
15
16 @timmer # 第一种调用方式;@timmer 相当于 test = timmer(test)
17 def test(name, age):
18 time.sleep(3)
19 print('test函数运行完毕,姓名【 %s】,年龄【%s】' % (name, age))
20 return '这是test的返回值'
21
22
23 res = test('alex', 18)
24 print(res)
装饰器加上参数

1 #!/usr/bin/env python
2 # -*- coding:utf-8 -*-
3 import time
4
5
6 def timmer(func):
7 def wrapper(*args, **kwargs):
8 start_time = time.time()
9 res = func(*args, **kwargs)
10 stop_time = time.time()
11 print('函数运行时间 %s' % (stop_time - start_time))
12 return res
13 return wrapper
14
15
16 @timmer # 第一种调用方式;@timmer 相当于 test = timmer(test)
17 def test(name, age):
18 time.sleep(3)
19 print('test函数运行完毕,姓名【 %s】,年龄【%s】' % (name, age))
20 return '这是test的返回值'
21
22
23 @timmer # 第一种调用方式;@timmer 相当于 test = timmer(test)
24 def test1(name, age,gender):
25 time.sleep(3)
26 print('test1函数运行完毕,姓名【 %s】,年龄【%s】,性别【%s】' % (name, age, gender))
27 return '这是test1的返回值'
28
29
30 res = test('alex', 18)
31 print(res)
32
33 res1 = test1('alex', 18, '男')
34 print(res1)
装饰器参数*args,**kwargs

1 #!/usr/bin/env python
2 # -*- coding:utf-8 -*-
3 ls = (11, 12, 13, 14, 15, 16, 17)
4 x, *_, z = ls
5 print(x) # 获取序列中的第一个值 结果:11
6 print(_) # 获取序列中的中间部分 结果:[12, 13, 14, 15, 16]
7 print(z) # 获取序列中的最后一个值 结果:17
补充解压序列

1 #!/usr/bin/env python
2 # -*- coding:utf-8 -*-
3 f1 = 11
4 f2 = 12
5 f1, f2 = f2, f1
6 print(f1) # 结果:12
7 print(f2) # 结果:11
补充交换2个变量的值

1 #!/usr/bin/env python
2 # -*- coding:utf-8 -*-
3
4
5 def auth_func(func):
6 def wrapper(*args, **kwargs):
7 username = input('用户名:').strip()
8 passwd = input('密码:').strip()
9 if username == 'alex' and passwd == '123':
10 res = func(*args, **kwargs)
11 return res
12 else:
13 print('用户名或密码错误!')
14 return wrapper
15
16
17 @auth_func
18 def index():
19 print('欢迎来到淘宝首页')
20
21
22 @auth_func
23 def home(name):
24 print('欢迎回家[%s]' % name)
25
26
27 @auth_func
28 def shopping_car(name):
29 print('[%s]购物车里有【%s, %s, %s】' % (name, '苹果', '桔子', '葡萄'))
30
31
32 index()
33 home('alex')
34 shopping_car('alex')
装饰器添加验证用户登录功能