Python装饰器之函数运行时间
目标
在《requests中文乱码问题》这篇文章中提到了两种解决方式,这两种方式究竟哪种方式是值得推荐的那?一般来说抓取网页与持久化储存是最耗时的,要想提高抓取效率就得从这两方面入手。那我们就从时间入手,在不改变原代码的情况下,可以使用装饰器来运算两种方式运行所需要的时间。
代码实现
1 | import time |
1 | >>>getHtml runs 100 times:0.19394637107849122s |
结论
答案很明显手动指定编码格式运行100次的平均时间更少,甚至连使用apparent_encoding根据网页内容分析编码方式的1/2都不到。手动指定编码格式只需要你查看网页源代码头部的charset就可以省下一半时间,所以我的建议是:如果出现中文乱码,手动指定编码格式即可。
其他
细心的小伙伴应该会发现在时间装饰器中,使用了@wraps(func),它是使用 from functools import wraps 导入的,那么它有什么作用那?
1 | @wraps接受一个函数来进行装饰,并加入了复制函数名称、注释文档、参数列表等等的功能。 |
这可以让我们在装饰器里面访问在装饰之前的函数的属性。例如在计算运行n次平均时间的函数中我们获取了函数的__name__ 属性,这也就使得这个函数更加通用了。如果去掉装饰器中的@wraps(func)这一句,那么在计算运行n次平均时间的函数中__name__ 属性获取到的就是wrapper了。
此外在计算运行n次平均时间的函数中我们还使用了f"{}{}{}",也就是f-string,亦称为格式化字符串常量(formatted string literals),是Python3.6新引入的一种字符串格式化方法。f-string在形式上是以 f 或 F 修饰符引领的字符串(f’xxx’或 F’xxx’),以大括号 {} 标明被替换的字段;f-string在本质上并不是字符串常量,而是一个在运行时运算求值的表达式。
1 | print(f'{func.__name__} runs {times} times:{sum(runtime_list) / times}s') |
在上面的例子中我们使用f-string格式化了函数属性,传递了变量,甚至可直接在其中进行运算。它还有很多有趣的用法,大家快去发掘吧!