python log函数_python要点-装饰器
大家有没有碰到过这种需求,扩展公司的历史项目,对功能进行扩展?拿到历史项目看源码的时候是不是头特别大,难上加难的是还要对其进行修改!!!今天要讲的是python中的重要功能-装饰器,其对满足前述的实现就提供了很友好的支持。
那么什么是装饰器,装饰器(Decorators)是 Python 的一个重要部分。简单地说:他们是修改其他函数的功能的函数。他们有助于让我们的代码更简短,代码修改起来也更容易,也更Pythonic(Python范儿)。大多数初学者不知道在哪儿使用它们,所以我将要分享下,哪些区域里装饰器可以让你的代码更简洁。 首先,让我们讨论下如何写你自己的装饰器。
预定场景:大家在很多时候实现功能的时候可能都需要实现对函数执行时间的统计,总的来说实现对函数执行时间的记时是很简单的,就是执行前执行后的时间差。那么更重要的是什么,就是如何让实现简单功能的函数能够更好的嵌入到我们的整个功能函数里,并且能够实现对其很好的调用、或者是更好的满足优秀的设计思想。
就上面的需求来说,实现的方式有很多:
1、在每个需要记录时间的函数里都写上时间计算的语句。
2、写一个计算时间的方法,在需要的地方进行调用。都是简单的方法,但如果需求量大了之后,从定义上、设计模式思想上来说,前两种方法,可能就不是那么美观了。最直观的就是,你可能需要写大量的重复语句或者是函数调用。
所以我们提倡使用今天要给大家讲的-python装饰器,装饰器的功能在前文也说到了,就是支持更友好的修改扩展历史功能以及写法上更pythonic。我们就以上述需求为例实现,上代码:
(1)函数装饰器
# coding:utf-8 import timedef decorator_time(func):def wrapper(*args, **kwargs):start_time = time.time()func(*args, **kwargs)end_time = time.time()use_time = end_time - start_timeprint("函数运行花费时间:{}".format(use_time))return funcreturn wrapper@decorator_time def add(a, b):time.sleep(1)print("a+b={}".format(a + b))add(1, 3)在上述代码中,decorator_time就是一个实现函数运行花费时间计算的装饰器,加入我们的原始函数功能就是实现加法的函数,如果我们要通过修改原函数代码实现,当然也可以,但是就破坏了原始代码的结构性,通过上面代码所使用的方法,是不是就简单多了,只需要在原函数上面加上@decorator_time即可,@是python中的语法糖,一种使用形式而已。
当然功能函数很多时候都是需要传入参数的,装饰器也是一样的,例如简单的日志功能,可能包含简单的等级信息,例如信息、警告、危险、错误等。那我们如何实现带参数的装饰器,如下:
# coding:utf-8 import timedef loginfo(level=1):def decorator_log(func):def wrapper(*args, **kwargs):if level == 1:print("这是一条显示信息。")if level == 2:print("这是一条警告信息。")if level == 3:print("这是一条错误信息。")func(*args, **kwargs)return funcreturn wrapperreturn decorator_log@loginfo(level=2) def add(a, b):print("a+b={}".format(a + b))add(1, 3)以上就是函数装饰器的简单实现以及运用。
(2)类装饰器
同样适用与上述场景,如果我们实现了多个函数装饰器,我们要同时使用多个装饰器的时候,怎么用呢,首先一个函数是可以同时使用多个装饰器的,依次将装饰器通过@写在上面即可。只不过,我们还可以用继承的的方式实现装饰器,这样,新写的装饰器就能包含历史的功能。例如,我们有一个写日志的装饰器,现在我们需要增加的就是如果日志等级较高,包含有错误等信息,希望装饰器可以将其通过发邮件的方法通知管理员。
那这个时候我们只需要新写一个继承原装饰器的新装饰器即可,只不过新的装饰器需要写入邮件发送的函数。类装饰器是通过类的__call__方法实现的。源码如下:
class logit():def __init__(self, logfile='out.log'):self.logfile = logfiledef __call__(self, func):def wrapped_function(*args, **kwargs):log_string = func.__name__ + " was called"print(log_string)# 打开logfile并写入with open(self.logfile, 'a') as opened_file:# 现在将日志打到指定的文件opened_file.write(log_string + 'n')# 现在,发送一个通知self.notify()return func(*args, **kwargs)return wrapped_functiondef notify(self):# logit只打日志,不做别的passclass email_logit(logit):''' 一个logit的实现版本,可以在函数调用时发送email给管理员 ''' def __init__(self, email='admin@myproject.com', *args, **kwargs): self.email = email super(email_logit, self).__init__(*args, **kwargs) def notify(self): # 发送一封email到self.email # 这里就不做实现了 pass使用方法和函数装饰器一样,只需要在原功能函数上面添加@email_logit即可。
装饰器主要适用于插入日志、性能测试、事务处理、缓存、权限校验等场景
总结
以上是生活随笔为你收集整理的python log函数_python要点-装饰器的全部内容,希望文章能够帮你解决所遇到的问题。
- 上一篇: c++ 文件读写_Java文件读写的常用
- 下一篇: python rpc微服务框架_grpc