Python装饰器
有这样一个函数,代码如下:
1
2
3
4
5
6
7
|
from functools import reduce def sum (): total = reduce ( lambda x,y: x + y, range ( 100000 )) print (total) sum () |
现在我们需要计算该函数执行所花的时间,代码如下
1
2
3
4
5
6
7
8
9
10
11
|
import time from functools import reduce def sum (): start_time = time.time() total = reduce ( lambda x,y: x + y, range ( 10000 )) end_time = time.time() print (total) print ( "time cost %fs" % (end_time - start_time)) sum () |
如果有几十个不同的函数需要计算函数执行所花的时候,每个都加上这几条语句的话,麻烦而且浪费时间,这里,我们就可以用到装饰器了,装饰器的使用在要使用的函数上面加上@以及装饰器的函数名
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
|
import time from functools import reduce def time_cost(func): def inner(): start_time = time.time() func() end_time = time.time() print ( "time cost %fs" % (end_time - start_time)) return inner @time_cost def sum (): total = reduce ( lambda x,y: x + y, range ( 10000 )) print (total) sum () |
此时sum函数将作为参数传递给time_cost函数,然后通过return语句执行inner语句中的内容,最后如果inner语句中有返回值,则将返回值重新赋值给sum函数
装饰器的功能是:
-
自动执行装饰器的函数并且将其下面的函数名当作参数进行传递
-
将装饰器函数中的返回值重新赋值给其下面的函数
python内部也内置了一些装饰器,例如:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
|
class Person: def __init__( self , name): self ._name = name @staticmethod def say(name): print ( "say" ) @classmethod def eat( cls ): print ( "eat" ) @property def name( self ): return self ._name |
装饰器下的函数也可以将里面的参数传递进来,例如:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
|
import time from functools import reduce def time_cost(func): def inner(arg): start_time = time.time() ret = func(arg) end_time = time.time() print ( "time cost %fs" % (end_time - start_time)) return ret return inner @time_cost def sum (n): total = reduce ( lambda x,y: x + y, range (n)) print (total) sum ( 100000 ) |
如果需要传递任意参数,可以这样:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
|
import time from functools import reduce def time_cost(func): def inner( * args, * * kwargs): start_time = time.time() ret = func( * args, * * kwargs) end_time = time.time() print ( "time cost %fs" % (end_time - start_time)) return ret return inner @time_cost def sum (n): total = reduce ( lambda x,y: x + y, range (n)) print (total) sum ( 100000 ) |
有时候根据需要也可以使用多层装饰器来简化操作,例如有些系统在进行操作的时候首先要保证用户处于登录状态,有的操作在这基础之上还需要对权限进行检测,因此这里可以用到双层装饰器,代码如下:
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
|
def check_login(func): def inner( * args, * * kwargs): if user_data[ "is_authed" ]: ret = func( * args, * * kwargs) return ret else : print ( "请登录" ) login() return inner def check_role(func): def inner( * args, * * kwargs): if user_data[ "user_type" ] = = 1 : ret = func( * args, * * kwargs) return func else : print ( "您没有权限" ) return inner @check_login @check_role def del_user(): user = input ( "请输入您要删除的用户: " ).strip() if user not in user_dict.keys(): print ( "该用户不存在" ) else : del user_dict[user] print ( "用户 %s 删除成功" % user) |
代码的执行顺序为: check_login()-->check_role-->del_user
来源:https://www.cnblogs.com/Kingway-Python/p/5846401.html