苏州建网站收费,在线做爰直播网站,韩国最新新闻事件,桂平做网站公司目录
一、Python元编程装饰器介绍
二、装饰器使用
1. 实现认证和授权功能
2.实现缓存功能
3.实现日志输出功能
三、附录
1. logging.basicConfig介绍
2. 精确到毫秒#xff0c;打印时间
方法一#xff1a;使用datetime
方法二#xff1a;使用time 一、Python元编程…目录
一、Python元编程装饰器介绍
二、装饰器使用
1. 实现认证和授权功能
2.实现缓存功能
3.实现日志输出功能
三、附录
1. logging.basicConfig介绍
2. 精确到毫秒打印时间
方法一使用datetime
方法二使用time 一、Python元编程装饰器介绍
Python元编程是指在Python中使用语言自身来创建、修改、或操纵其它代码的能力。其中装饰器是元编程中最常见的一种技术。
装饰器是一种函数其接受一个函数作为参数并返回另一个函数。这通常被用于修改或扩展现有函数的功能。
装饰器在Python中的优点包括
使代码更加模块化通过装饰器我们可以将不同的功能逻辑分离到不同的装饰器中使代码更加模块化。简化代码使用装饰器可以避免代码重复使代码更加简洁明了。提高代码的可重用性由于装饰器本身就是一种可重用的代码模式所以可以提高代码的可重用性。
装饰器在Python中的缺点包括
可读性较差有时装饰器会让代码变得更加难以理解和调试。装饰器的嵌套如果使用多个装饰器来实现某个功能可能会导致装饰器的嵌套过于复杂。
装饰器在应用程序开发中的应用场景包括
认证和授权通过装饰器可以在需要进行认证和授权的函数前添加一个用于检查权限的装饰器。缓存使用装饰器可以轻松地添加缓存逻辑避免重复计算。日志使用装饰器可以很方便地处理日志输出。
装饰器的使用方式如下
def my_decorator(func):def wrapper(*args, **kwargs):# beforeprint(before...)result func(*args, **kwargs)# afterprint(after...)return result# 返回包装后的函数return wrappermy_decorator
def say_test():print(test)say_test()
运行结果 before... test after... 二、装饰器使用
1. 实现认证和授权功能
下面以一个简单的例子来说明如何使用Python元编程装饰器实现认证和授权功能。
假设我们有一个网络应用程序其中包含一些需要身份验证的受保护页面。我们希望使用装饰器来实现身份验证和授权功能。
首先我们可以定义一个装饰器函数authenticate用于验证用户身份
在这个装饰器函数中我们将原始函数func封装成一个新的函数wrapper。在wrapper函数中我们首先检查当前用户是否已经通过身份验证如果是则调用原始函数func并将它的参数传递给它否则抛出一个ValueError异常。
接下来我们定义一个装饰器函数authorize用于授权用户访问某个页面
在这个装饰器函数中我们首先接受一个roles列表用于指定允许访问该页面的用户角色。然后我们返回一个新的装饰器函数decorator它接受原始函数func作为参数并返回一个新的函数wrapper。在wrapper函数中我们首先检查当前用户的角色是否在允许访问该页面的角色列表中如果是则调用原始函数func并将它的参数传递给它否则抛出一个ValueError异常。
现在我们可以将这两个装饰器应用到我们的页面处理函数中。例如
def authenticate(func):def wrapper(*args, **kwargs):# beforeprint(authenticate before...)#假设在args[0]中保存了当前用户的信息if args[0].is_authenticated:# afterprint(authenticate after...)result func(*args, **kwargs)return resultelse:# afterprint(authenticate after...)raise ValueError(用户未认证User is not authenticated)# 返回包装后的函数return wrapperdef authorize(roles):def decorator(func):def wrapper(*args, **kwargs):# 假设在args[0]中保存了当前用户的信息if args[0].role in roles:result func(*args, **kwargs)return resultelse:# raise ValueError(用户未授权User is not authorized)print(用户未授权)# 返回包装后的函数return wrapperreturn decoratorclass User():def __init__(self, name, role):self.name nameself.role roleself.is_authenticated Trueauthenticate
authorize([admin, editor])
def secret_page(user):return This is the secret pageuser User(Alice, admin)
res secret_page(user)
print(res)user User(Tom, guest)
res secret_page(user)
# print(res)
运行结果 authenticate before... authenticate after... This is the secret page authenticate before... authenticate after... 用户未授权 在这个例子中我们定义了一个User类其中包含用户的名称、角色和身份验证状态。然后我们将authenticate和authorize装饰器应用到secret_page函数中authenticate用于验证用户身份authorize用于授权用户访问该页面。在执行secret_page(user)时Python会按照从上到下的顺序依次应用装饰器并检查当前用户的身份和角色是否满足要求。如果满足要求则输出页面内容否则抛出异常。
以上就是使用Python元编程装饰器实现身份验证和授权功能的一个简单例子。当然在实际开发中我们需要更加细致地设计和实现这些功能以确保应用程序的安全性和可靠性。
2.实现缓存功能
下面以一个简单的例子来说明如何使用Python元编程装饰器实现缓存功能。
假设我们有一个函数calculate它接受一个整数作为参数并计算该整数的阶乘。现在我们希望使用装饰器来缓存该函数的计算结果以提高程序的性能。
首先我们可以定义一个装饰器函数cache用于缓存函数调用的结果
在这个装饰器函数中我们首先定义一个cache_dict字典用于保存函数调用的结果。然后我们返回一个新的函数wrapper它接受任意数量的参数*args这些参数将被传递给原始函数func。在wrapper函数中我们首先检查参数args是否已经在cache_dict中如果是则直接返回该结果否则调用原始函数func将结果保存在cache_dict中并返回该结果。
接下来我们可以将cache装饰器应用到calculate函数中。例如
def cache(func):cache_dict {}def wrapper(*args, **kwargs):if args in cache_dict:return cache_dict[args]else:result func(*args)cache_dict[args] resultreturn resultreturn wrappercache
def calculate(n):if n 0:return 1else:return n * calculate(n-1)res calculate(5) # 第一次调用需要计算并缓存结果
print(res)
res calculate(5) #第二次调用直接从缓存中获取结果
print(res)运行结果 120 120 在这个例子中我们定义了一个calculate函数它计算给定整数的阶乘。然后我们将cache装饰器应用到该函数中以实现缓存功能。在执行calculate(n)时Python会自动按照装饰器的规则调用cache(wrapper)函数将原始的calculate函数包装成一个新的函数并返回该函数对象。在第一次调用calculate(5)时Python会先调用wrapper(5)函数并将结果缓存在cache_dict中。在第二次调用calculate(5)时Python直接从cache_dict中获取结果并返回该结果。这样整个计算过程只需要进行一次大大提高了程序的性能。
以上就是使用Python元编程装饰器实现缓存功能的一个简单例子。当然在实际开发中我们需要更加细致地设计和实现缓存策略以确保缓存的准确性和有效性。
3.实现日志输出功能
下面以一个简单的例子来说明如何使用Python元编程装饰器实现处理日志输出功能。
假设我们有一个函数calculate它接受一个整数作为参数并计算该整数的阶乘。现在我们希望在调用该函数时自动记录日志输出以便于调试和监控程序的运行情况。
首先我们可以定义一个装饰器函数log用于记录函数调用和返回结果
在这个装饰器函数中我们首先使用Python标准库中的logging模块来设置日志输出格式和目标文件。然后我们返回一个新的函数wrapper它接受任意数量的位置参数*args和关键字参数**kwargs这些参数将被传递给原始函数func。在wrapper函数中我们首先使用logging.debug()函数记录函数调用的信息包括函数名、位置参数和关键字参数。然后调用原始函数func将结果保存在result变量中。最后再使用logging.debug()函数记录函数返回的信息包括函数名和返回结果。
接下来我们可以将log装饰器应用到calculate函数中。例如
import logging
import oslogging.basicConfig(levellogging.DEBUG,format%(asctime)s %(filename)s[line:%(lineno)d] %(levelname)s %(message)s,# datefmt%a, %d, %b, %Y %H:%M:%S, # 精确到秒datefmt%Y-%m-%d %H:%M:%S, # 精确到秒filenameoutput.log,filemodew)def log(func):def wrapper(*args, **kwargs):logging.debug(Calling function {} with args: {}, kwargs: {}.format(func.__name__, args, kwargs))result func(*args, **kwargs)logging.debug(Function {} returned: {}.format(func.__name__, result))return resultreturn wrapperlog
def calculate(n):if n 0:return 1else:time.sleep(0.5)return n * calculate(n - 1)# 调用函数同时记录输出
print(calculate(5))print(os.getcwd()) #output.log文件位置
运行结果 120 D:\code\AutoTest\common\Metaprogramming output.log 在这个例子中我们定义了一个calculate函数它计算给定整数的阶乘。然后我们将log装饰器应用到该函数中以实现记录日志输出功能。在执行calculate(n)时Python会自动按照装饰器的规则调用log(wrapper)函数将原始的calculate函数包装成一个新的函数并返回该函数对象。在调用calculate(5)时Python会自动调用wrapper(5)函数并记录函数调用和返回的信息到指定的日志文件中。这样我们就可以方便地查看函数的调用过程和计算结果从而提高程序的可读性和可维护性。
以上就是使用Python元编程装饰器实现处理日志输出功能的一个简单例子。当然在实际开发中我们还需要更加细致地设计和实现日志输出策略以满足实际的需求。
三、附录
1. logging.basicConfig介绍
logging是Python标准库中的一个模块用于记录应用程序运行时的日志信息。其中basicConfig函数是logging模块中的一个配置函数用于对logging进行基本配置。
basicConfig函数可以接受多个参数用于设置日志的格式、日志级别、输出位置等信息。常用的参数如下
level设置日志级别可选值有DEBUG、INFO、WARNING、ERROR和CRITICAL默认为WARNING。format设置日志格式可选值有asctime、name、levelname、message等参数例如[%(asctime)s] [%(levelname)s] %(message)s。filename指定日志输出到文件如果不指定则默认输出到控制台。filemode指定日志输出文件的打开模式可选值有w、a等。
下面是一个简单的例子
import logginglogging.basicConfig(levellogging.INFO, format%(asctime)s %(levelname)s %(message)s)logging.info(info message)
logging.warning(warning message)这段代码设置了日志级别为INFO格式为时间 日志级别 日志信息并输出了一个INFO级别的日志和一个WARNING级别的日志。输出结果如下
2021-09-30 14:20:10,315 INFO info message
2021-09-30 14:20:10,315 WARNING warning message注意如果需要对不同的模块分别进行日志记录则需要创建不同的Logger对象并对其进行配置。可以使用Logger类中的方法来设置日志级别、日志格式、输出位置等信息例如addHandler方法可以添加一个处理器来指定日志输出到文件或网络等位置。
2. 精确到毫秒打印时间
方法一使用datetime
你可以使用 datetime 模块来输出当前时间精确到毫秒
from datetime import datetimenow datetime.now()
micro_sec now.microsecond // 1000 # 计算毫秒部分
print(now.strftime(%Y-%m-%d %H:%M:%S.) str(micro_sec).zfill(3))在这个代码中我们使用 datetime.now() 函数获取当前时间然后使用 microsecond 属性获取微秒部分并将其除以 1000 得到毫秒。最后我们将毫秒部分用 zfill(3) 进行前导零填充并拼接成完整的时间字符串。
方法二使用time
import timet time.time()
s time.strftime(%Y-%m-%d %H:%M:%S., time.localtime(t)) (%d % (t % 1 * 1000)).zfill(3)
print(s)在这个代码中我们没有使用 %f而是手动计算并格式化毫秒部分。具体来说我们使用了时间戳 t 对 1 取模获得秒的小数部分乘以 1000 得到毫秒再使用 zfill(3) 来对毫秒部分进行前导零填充。
这种方式需要手动计算毫秒部分并且可能会有一些精度损失但是在 Python 2.x 中可以工作。