簡體   English   中英

成長python列表的最佳實踐

[英]best practice to grow python list

我的列表表列表很大,我需要向其中添加更多列。

tbl = [range(200),range(200),range(200),...]
newCol = [val1, val2]

我看到它的方式可以做到這一點:

for idx,val in enumerate(tbl)
    tbl[idx] = newCol + val

要么

colRep = [newCol]*len(tbl)
mgr = itertools.izip(colRep,tbl)
newTbl = [ itertools.chain(*elem) for elem in mgr]

一個真的比另一個好嗎? 有更好的方法嗎?

出於可讀性考慮,簡單的列表理解即可:

In [28]: tbl = [range(2),range(3),range(4)]
In [29]: [newCol + list(elt) for elt in tbl]
Out[29]: 
[['val1', 'val2', 0, 1],
 ['val1', 'val2', 0, 1, 2],
 ['val1', 'val2', 0, 1, 2, 3]]

請注意,在Python3中, range返回范圍對象,而不是列表。 因此,為了使代碼與Python2和Python3兼容,我將newCol + elt更改為newCol + list(elt)

如果您希望就地修改tbl ,則可以使用

tbl[:] = [newCol + list(elt) for elt in tbl]

請注意,在比較性能之前,我們需要確定所需的結果,以免最終將蘋果與橙子進行比較。

for-loop就地修改tbl 到位重要嗎?

zip/chain不對tbl進行就地修改,而是生成一個迭代器列表:

In [47]: newTbl
Out[47]: 
[<itertools.chain at 0x7f5aeb0a6750>,
 <itertools.chain at 0x7f5aeb0a6410>,
 <itertools.chain at 0x7f5aeb0a6310>]

那可能就是您想要的,但是比較這兩段代碼的性能將是不公平的,因為iterators延遲枚舉iterators各項的過程。 就像計時房子和考慮油漆房子之間的區別一樣。

為了使比較更公平,我們可以使用list來消耗迭代器:

newTbl = [ list(itertools.chain(*elem)) for elem in mgr]

為了基准測試各種選項的性能,您可以使用timeit如下所示:

import timeit
import itertools

tbl = [range(2),range(3),range(4)]
newCol = ['val1', 'val2']

stmt = {
    'for_loop' : '''\
for idx,val in enumerate(tbl):
    tbl[idx] = newCol + val
''',
    'list_comp': '''tbl = [newCol + elt for elt in tbl]''',
    'inplace_list_comp': '''tbl[:] = [newCol + elt for elt in tbl]''',
    'zip_chain': '''
colRep = [newCol]*len(tbl)
mgr = itertools.izip(colRep,tbl)
newTbl = [ list(itertools.chain(*elem)) for elem in mgr]
'''

}
for s in ('for_loop', 'list_comp', 'inplace_list_comp', 'zip_chain'):
    t = timeit.timeit(
        stmt[s], 
        setup='from __main__ import newCol, itertools; tbl = [range(200)]*10**5',
        number=10)
    print('{:20}: {:0.2f}'.format(s, t))

產量

for_loop            : 1.12
list_comp           : 1.21
inplace_list_comp   : 1.26
zip_chain           : 4.40

因此, for_loop可能會略快一些。 確保在更接近您實際用例的地方使用tbl進行檢查。 timeit結果可能由於多種原因而有所不同,包括硬件,操作系統和軟件版本。

還應注意,如果這小段代碼不是您實際代碼中的重要瓶頸,那么這可能是毫無意義的預優化 例如,如果您的實際代碼在此列表理解中花費1.21秒,而在其他地方花費1000秒,那么此處的十分之一秒的改進將是微不足道的。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM