我正在使用cProfile
在通过列表理解处理字符串的脚本上运行基准测试。我想优化的目标线看起来像这样:
signals = [('prefix' + str(day) + '_' + s) for s in signals]
其中day
是整数。
此特定行使用了整个运行时间的33%。当然,在执行过程中它被称为百万次。
我尝试过几个明显的替代方案,包括''.join('prefix', str(day), '_', s)
,'prefix{:}_'.format(day)
,并使用numpy.core.defchararray.add
将通过numpy.tile
创建的前缀数组与signals
连接起来。它们的速度比列表理解慢2倍。
此线路的速度优化是否还有空间?
答案 0 :(得分:5)
这至少应该带来最小的改善:
# First precalculate the static part of the string
template = 'prefix%s_' % day + '%s'
# Then, use the %s string interpolation instead of joining strings with '+'
# -->> Note: this proved to be wrong later...
signals = [template % s for s in signals]
# Alternatively you could use map to compare efficiency (be aware of differences between python 2 and 3)
signals = map(template.__mod__, signals)
str.format
比%s
插值更贵,所以我不会尝试。
现在让我们比较一下时间。你的方法:
>>> import timeit
>>> day = 45
>>> signals = ['aaaa', 'bbbb', 'cccccc', 'dddddddddddd']
>>> timeit.timeit("[('prefix' + str(day) + '_' + s) for s in signals]", 'from __main__ import day, signals')
1.35095184709592
我的第一个方法
>>> template = 'prefix%s_' % day + '%s'
>>> timeit.timeit("[template % s for s in signals]", 'from __main__ import template, signals')
0.7075940089748229
我的第二种方法
>>> timeit.timeit("map(template.__mod__, signals)", 'from __main__ import template, signals')
0.9939713030159822
因此,具有列表理解的模板的预先计算似乎获胜。还有一些事情需要考虑,例如,如果发电机对你来说足够好。
从有意义的评论中指出的信息编辑,我添加了另一个解决方案:在紧密循环内部我们只将两个字符串连接在一起,所以我们可以直接连接它们而不是%-formatting < / p>
>>> template = 'prefix%s_' % day
>>> timeit.timeit("[template + s for s in signals]", 'from __main__ import template, signals')
0.39771016975851126
目前哪个是胜利者。
答案 1 :(得分:1)
尝试过:
signals = ['prefix{0}_{1}'.format(day, s) for s in signals]
作为基线,如果你只使用元组而不是字符串会怎么样?:
signals = [(day, s) for s in signals]
答案 2 :(得分:1)
这可以更快
import numpy as np
signal = [x for x in range(9000)]
length = len(signal)
prefArray = np.array(['prefix']*length )
dArray = np.array([str(day)]*length )
cArray = np.array(['_']*length )
sArray = np.array(["%s"%x for x in signal])
firstArray = np.core.defchararray.add(prefArray, dArray)
secondArray = np.core.defchararray.add(cArray, sArray)
result = np.core.defchararray.add(firstArray,secondArray)
print result