AI智能
改变未来

day010|python之装饰器


装饰器02

[TOC]

1 装饰器的语法糖

1.1 定义

为了简洁而优雅地使用装饰器,Python提供了专门的装饰器语法来取代index=timer(index)的形式,需要在被装饰对象的正上方单独一行添加@timer,当解释器解释到@timer时就会调用timer函数,且把它正下方的函数名当做实参传入,然后将返回的结果重新赋值给原函数名

1.2 基本使用

import timedef timmer(f):def wrapper(*args, **kwargs):start = time.time()res = f(*args, **kwargs)stop = time.time()print(\'run time is %s\' % (stop - start))return resreturn wrapper@timmer  # index = timmer(index)def index():time.sleep(1)print(\'from index\')@timmer  # home = time(home)def home(name):time.sleep(2)print(\'welcome to %s\' % name)return 123index()res = home("ccc")print(res)# from index# run time is 1.0003390312194824# welcome to ccc# run time is 2.0008108615875244# 123

2 有参装饰器

2.1 基本用法

@auth(driver=\'file\')def index():pass@auth(driver=\'mysql\')def home():pass

2.2 示例

import timedef login(x, engine=\'file\'):def auth(func):def wrapper(*args, **kwargs):print("========>", x)inp_user = input("username>>>>:").strip()inp_pwd = input("password>>>:").strip()if engine == "file":print("基于file认证")if inp_user == "egon" and inp_pwd == "123":print(\'login successful\')res = func(*args, **kwargs)return reselse:print(\'username or password error\')elif engine == \'mysql\':print("基于mysql认证")elif engine == "ldap":print("基于ldap认证")else:print("未知认证来源")return wrapperreturn auth@login(11, engine=\'file\')  # @auth  # index = auth(index)  # index=wrapperdef index():time.sleep(1)print(\'from index\')@login(22, engine=\'file\')  # @auth  # home=auth(home)  # home=wrapperdef home(name):time.sleep(2)print(\'home page,welcome %s\' % name)return 123index()home(\'egon\')# ========> 11# username>>>>:egon# password>>>:123# 基于file认证# login successful# from index# ========> 22# username>>>>:egon# password>>>:123# 基于file认证# login successful# home page,welcome egon

3叠加多个装饰器

3.1 基本用法

@deco3@deco2@deco1def index():pass
# 本质index=deco3(deco2(deco1(index)))

3.2 示例

def outter1(func1):  # func1 = wrapper2的内存地址print(\'============>outter1\')def wrapper1(*args, **kwargs):print(\'=============wrapper1\')res1 = func1(*args, **kwargs)return res1return wrapper1def outter2(func2):  # func2 = wrapper3的内存地址print(\'============>outter2\')def wrapper2(*args, **kwargs):print(\'=============wrapper2\')res2 = func2(*args, **kwargs)return res2return wrapper2def outter3(func3):  # func3 = index的内存地址print(\'============>outter3\')def wrapper3(*args, **kwargs):print(\'=============wrapper3\')res3 = func3(*args, **kwargs)return res3return wrapper3# index = wrapper1的内存地址@outter1  # outter1(wrapper2的内存地址)-->wrapper1的内存地址@outter2  # outter2(wrapper3的内存地址)-->wrapper2的内存地址@outter3  # outter3(index的内存地址)-->wrapper3的内存地址def index():print(\'from index\')print(\'*\'*25)# print(index)index()# ============>outter3# ============>outter2# ============>outter1# *************************# =============wrapper1# =============wrapper2# =============wrapper3# from index
import timedef timmer(func):def wrapper1(*args, **kwargs):start = time.time()res = func(*args, **kwargs)stop = time.time()print(\'run time is:%s\' % (stop - start))return resreturn wrapper1def login(x, engine=\'file\'):def auth(func):def wrapper2(*args, **kwargs):print("========>", x)inp_user = input("username>>>>:").strip()inp_pwd = input("password>>>:").strip()if engine == "file":print("基于file认证")if inp_user == "egon" and inp_pwd == "123":print(\'login successful\')res = func(*args, **kwargs)return reselse:print(\'username or password error\')elif engine == \'mysql\':print("基于mysql认证")elif engine == "ldap":print("基于ldap认证")else:print("未知认证来源")return wrapper2return auth# 场景一@timmer@login(11, engine=\'file\')def index():time.sleep(1)print(\'from index\')index()# ========> 11# username>>>>:egon# password>>>:123# 基于file认证# login successful# from index# run time is:9.147817134857178# 场景二@login(11, engine=\'file\')@timmerdef index():time.sleep(1)print(\'from index\')index()# ========> 11# username>>>>:egon# password>>>:123# 基于file认证# login successful# from index# run time is:1.0001623630523682

4 wraps装饰器

4.1 定义

  • functools模块下提供一个装饰器wraps专门用来帮我们保留原函数的文档和函数名属性,修正装饰器

4.2 示例

import timefrom functools import wrapsdef timmer(func):@wraps(func)def wrapper(*args, **kwargs):start = time.time()res = func(*args, **kwargs)stop = time.time()print(\'run time is:%s\' % (stop - start))return resreturn wrapper@ timmerdef index():"""index函数"""time.sleep(1)print(\'from index\')help(index)

5 匿名函数

"""def func(x, y):  # func=函数的内存地址return x+y匿名函数:没有名字的函数应用场景:临时用一次,通常用于与其他函数配合使用"""# 无用调用方式f = lambda x, y: x+yprint(f)res = f(1, 2)print(res)# 调用方式1res = (lambda x, y: x+y)(1, 2)print(res)# 调用方式2salaries = {"egon": 1000,"alex": 2000,"jack": 3000,"rose": 4000}# 求薪资最高的那个人的名字def get_salary(name):return salaries[name]print(max(salaries, key = get_salary))  # roseprint(max(salaries, key=lambda name: salaries[name]))  # roseprint(min(salaries, key=lambda name: salaries[name]))  # egonprint(sorted(salaries))  # [\'alex\', \'egon\', \'jack\', \'rose\']print(sorted(salaries, key=lambda name: salaries[name]))  # [\'egon\', \'alex\', \'jack\', \'rose\']print(sorted(salaries, key=lambda name: salaries[name], reverse=True))  # [\'rose\', \'jack\', \'alex\', \'egon\']# 返回绝对值print(abs(-11))  # 11print(abs(0))  # 0print(abs(11))  # 11# 如果是空或布尔值为真则返回Trueprint(all(\'\'))  # Trueprint(all([]))  # Trueprint(all([11, 22, 333, 0]))  # False# 只要有一个值的布尔值为真就返回Trueprint(any(\'\'))  # Falseprint(any([]))  # Falseprint(any([0, None, \'\', 1]))  # Trueprint(any([0, None, \'\']))  # False# ASCⅡ表:65-90 A-Zprint(chr(65))  # 数字->字母Aprint(ord(\'A\'))  # 字母->数字65print(chr(90))  # Z# 进制转换print(bin(11))  # 十进制->二进制 0b1011print(oct(11))  # 十进制->八进制 0o13print(hex(11))  # 十进制->十六进制 0xb# 工厂函数intfloatstrlisttupledictsetboolbytes# 查看对象是否可调用print(callable(len))  # True# 面向对象重点classmethodstaticmethodsetattrgetattrdelattrhasattrdirexecl = eval("[1, 2, 3]")print(l[0])  # 1with open(\'user1.txt\', mode=\'wt\', encoding=\'utf-8\') as f:dic = {"ccc": "123", "zzz": "456", "yyy": "789"}f.write(str(dic))with open(\'user1.txt\', mode=\'rt\', encoding=\'utf-8\') as f:data = f.read()print(data, type(data))  # {\'ccc\': \'123\', \'zzz\': \'456\', \'yyy\': \'789\'} <class \'str\'>dic = eval(data)print(dic["ccc"])  # 123
赞(0) 打赏
未经允许不得转载:爱站程序员基地 » day010|python之装饰器