我读到List comprehension without [ ] in Python所以现在我知道了
''.join([str(x) for x in mylist])
比
快''.join(str(x) for x in mylist)
因为"列表推导得到了高度优化"
所以我认为优化依赖于for
表达式的解析,看mylist
,计算它的长度,并使用它来预先分配精确的数组大小,这节省了大量的再分配。
使用''.join(str(x) for x in mylist)
时,join
会盲目地接收一个生成器,并且必须在不事先知道大小的情况下构建其列表。
但现在考虑一下:
mylist = [1,2,5,6,3,4,5]
''.join([str(x) for x in mylist if x < 4])
python如何决定列表理解的大小?它是根据mylist
的大小计算的,并且在迭代完成时缩小(如果列表很大并且条件过滤掉99%的元素,这可能非常糟糕),或者它是否会恢复为& #34;事先不知道大小&#34;情况?
没有条件:
import timeit
print(timeit.timeit("''.join([str(x) for x in [1,5,6,3,5,23,334,23234]])"))
print(timeit.timeit("''.join(str(x) for x in [1,5,6,3,5,23,334,23234])"))
收益率(如预期):
3.11010817019474
3.3457350077491026
条件:
print(timeit.timeit("''.join([str(x) for x in [1,5,6,3,5,23,334,23234] if x < 50])"))
print(timeit.timeit("''.join(str(x) for x in [1,5,6,3,5,23,334,23234] if x < 50)"))
的产率:
2.7942209702566965
3.0316467566203276
所以条件listcomp仍然更快。
答案 0 :(得分:12)
列表理解不预先确定列表的大小,即使它们完全可以。您假设存在未实际完成的优化。
列表理解更快,因为所有迭代器机制以及进入和退出genexp堆栈帧的工作都有成本。列表理解不需要支付这笔费用。