<>前言

这篇博客提及三个关于python循环的优化细节,如有其他一些优化的方案,欢迎留言分享~QWQ

<>合理使用生成器(generator)和yield

在谈这个环节之前,我们先回顾一波何为生成器及何为yield

要理解yiled还需要理解生成器,而要理解生成器,首先需要理解迭代器。

迭代器:

所有你可以用在for...in...语句中的都是可迭代的:比如lists,strings,files
…因为这些可迭代的对象你可以随意的读取所以非常方便易用,但是你必须把它们的值放到内存里,当它们有很多值时就会消耗太多的内存.

生成器:

生成器也是迭代器的一种,但是你只能迭代它们一次.原因很简单,因为它们不是全部存在内存里,它们只在要调用的时候在内存里生成,下面看两个例子:

1、生成器
>>> mygenerator = (x*x for x in range(3)) >>> for i in mygenerator: ...
print(i) ... 0 1 4 >>>
2、list列表
>>> listTest = [x*x for x in range(3)] >>> for i in listTest: ... print(i) ...
0 1 4
区别:
>>> print(listTest) [0, 1, 4] >>> print(mygenerator) <generator object <genexpr
> at 0x000001FAB703DE60>
生成器和迭代器的区别就是用()代替[],还有你不能用for i in mygenerator
第二次调用生成器:首先计算0,然后会在内存里丢掉0去计算1,直到计算完4.

Yield

Yield的用法和关键字return差不多,下面的函数将会返回一个生成器:
>>> def createGenerator(): ... mylist = range(3) ... for i in mylist: ... yield
i*i ... >>> mygenerator = createGenerator() >>> print(mygenerator) <generator
object createGenerator at 0x000001FAB703DE60> >>>
要理解Yield你必须先理解当你调用函数的时候,函数里的代码并没有运行.函数仅仅返回生成器对象,这就是它最微妙的地方。

下面看两个例子:
1、仅仅分别产生generator与list对象
import time import sys t1 = time.time() arange = (i for i in range(2000000))
print("brange size:") print(sys.getsizeof(arange)) t2 = time.time() print(
"arange time:") print(t2-t1) t3 = time.time() brange = [i for i in range(2000000
)] print("brange size:") print(sys.getsizeof(brange)) t4 = time.time() print(
"brange time:") print(t4-t3) # brange size: # 88 # arange time: # 0.0 # brange
size: # 17632632 # brange time: # 0.12857437133789062
使用()得到的是一个generator对象,所需要的内存空间与列表的大小无关,所以效率会高一些。至于原理见上面的生成器原理部分。

2、供for循环使用
import time t1 = time.time() arange = (i for i in range(20000000)) for x in
arange: pass t2 = time.time() print("arange time:") print(t2-t1) t3 = time.time(
) brange = [i for i in range(20000000)] for x in brange: pass t4 = time.time()
print("brange time:") print(t4-t3) # arange time: # 1.7372145652770996 # brange
time: # 1.8086597919464111
这里虽然说并没有快上多少,但不要忘记了,在时间更优的情况下,生成器generator内存空间占用更是完爆list,所以说,循环尽量用生成器!!!!

<>优化循环之位置

这个其实不必多说和解释,循环之外能做的事不要放在循环内,比如下面的优化基本可以快一倍:
import time test = "123" length_test = len(test) t1 = time.time() arange = (i
for i in range(4000000)) for x in arange: ap = length_test t2 = time.time()
print("arange time:") print(t2-t1) t3 = time.time() brange = (i for i in range(
4000000)) for x in brange: bp = len(test) t4 = time.time() print("brange time:")
print(t4-t3) # arange time: # 0.460693359375 # brange time: # 0.8602120876312256
<>while 1 比 while True 更快

2333,这个你可能不相信,但请看例子:
import time def while_1(): t1 = time.time() n = 100000000 while 1: n -= 1 if n
<= 0: break t2 = time.time() print("while1 time:") print(t2-t1) def while_true()
: t3 = time.time() n = 100000000 while True: n -= 1 if n <= 0: break t4 = time.
time() print("while_true time:") print(t4-t3) if __name__ == '__main__': while_1
() while_true() # while1 time: # 5.369367837905884 # while_true time: #
5.293442487716675
至于原理:
True是一个全局变量,而非关键字

技术
下载桌面版
GitHub
Gitee
SourceForge
百度网盘(提取码:draw)
云服务器优惠
华为云优惠券
腾讯云优惠券
阿里云优惠券
Vultr优惠券
站点信息
问题反馈
邮箱:[email protected]
吐槽一下
QQ群:766591547
关注微信