我正在尝试加速以下python代码:
for j in range(4,len(var_s),3):
mag_list.append(float(var_s[j]))
mag_list = [value for value in mag_list if value != 99.]
med_mag = np.median(mag_list)
有没有一种很好的方法将两个for循环合并为一个?这样,它真的很慢。我需要的是从var_s列表中提取每个第三个条目,从五分之一开始,如果该条目的值不等于99.在结果列表中,我需要中位数。 谢谢!
答案 0 :(得分:12)
您可以尝试:
mag_list = [value for value in var_s[4::3] if value != 99.]
取决于var_s
,您可能会使用itertools.islice(var_s,4,None,3)
做得更好,但这肯定需要时间知道。
如果你一直坚持使用numpy,也许你会做得更好:
vs = np.array(var_s[4::3],dtype=np.float64) #could slice after array conversion too ...
med_mag = np.median(vs[vs!=99.])
同样,这需要时间来看看它相对于其他人的表现。
答案 1 :(得分:4)
mag_list = filter(lambda x: x != 99, var_s[4::3])
好的,这里有一些timeit
试验,全部在Python 2.7.2中:
设置:
>>> from random import seed, random
>>> from timeit import Timer
>>> from itertools import islice, ifilter, imap
>>> seed(1234); var_s = [random() for _ in range(100)]
使用for循环:
>>> def using_for_loop():
... mag_list = []
... for j in xrange(4, len(var_s), 3):
... value = float(var_s[j])
... if value != 99: mag_list.append(value)
...
>>> Timer(using_for_loop).timeit()
11.596584796905518
使用地图和过滤器:
>>> def using_map_filter():
... map(float, filter(lambda x: x != 99, var_s[4::3]))
...
>>> Timer(using_map_filter).timeit()
8.643505096435547
使用islice,imap,ifilter:
>>> def using_itertools():
... list(imap(float, ifilter(lambda x: x != 99, islice(var_s, 4, None, 3))))
...
>>> Timer(using_itertools).timeit()
11.311019897460938
使用列表理解和islice:
>>> def using_list_comp():
... [float(v) for v in islice(var_s, 4, None, 3) if v != 99]
...
>>> Timer(using_list_comp).timeit()
8.52650499343872
>>>
总之,使用islice的列表理解是最快的,其次是地图和过滤器的使用速度稍慢。
答案 2 :(得分:1)
for j in range(4,len(var_s),3):
value = float(var_s[j])
if value != 99:
mag_list.append(value)
med_mag = np.median(mag_list)