在使用Python编程时,是否可以为将填充已知数量的项目的列表保留内存,以便在构建列表时不会多次重新分配列表?我查看了文档中的Python列表类型,但没有找到任何似乎这样做的东西.但是,这种类型的列表构建显示在我的代码的几个热点中,所以我想尽可能高效.
编辑:另外,用像Python这样的语言做这样的事情是否有意义?我是一个相当有经验的程序员,但是对Python很陌生并且仍然对它的做事方式有所了解.Python是否在内部将所有对象分配到单独的堆空间中,从而无法尝试最小化分配,或者是直接存储在列表中的诸如整数,浮点数等原语?
这里有四种变体:
增量列表创建
"预先分配"清单
array.array()
numpy.zeros()
python -mtimeit -s"N=10**6" "a = []; app = a.append;"\ "for i in xrange(N): app(i);" 10 loops, best of 3: 390 msec per loop python -mtimeit -s"N=10**6" "a = [None]*N; app = a.append;"\ "for i in xrange(N): a[i] = i" 10 loops, best of 3: 245 msec per loop python -mtimeit -s"from array import array; N=10**6" "a = array('i', [0]*N)"\ "for i in xrange(N):" " a[i] = i" 10 loops, best of 3: 541 msec per loop python -mtimeit -s"from numpy import zeros; N=10**6" "a = zeros(N,dtype='i')"\ "for i in xrange(N):" " a[i] = i" 10 loops, best of 3: 353 msec per loop
它表明这[None]*N
是最快的,array.array
在这种情况下是最慢的.
您可以创建已知长度的列表,如下所示:
>>> [None] * known_number
看看这个:
In [7]: %timeit array.array('f', [0.0]*4000*1000) 1 loops, best of 3: 306 ms per loop In [8]: %timeit array.array('f', [0.0])*4000*1000 100 loops, best of 3: 5.96 ms per loop In [11]: %timeit np.zeros(4000*1000, dtype='f') 100 loops, best of 3: 6.04 ms per loop In [9]: %timeit [0.0]*4000*1000 10 loops, best of 3: 32.4 ms per loop
所以不要使用array.array('f', [0.0]*N)
,使用array.array('f', [0.0])*N
或numpy.zeros
.
在大多数日常代码中,您不需要这样的优化.
但是,当列表效率成为一个问题时,您应该做的第一件事是用array
模块中的类型化替换泛型列表,这样更有效.
以下是如何创建400万个浮点数的列表:
import array lst = array.array('f', [0.0]*4000*1000)