我有一个这样的列表(为了简单起见,我使用整数渐进数字,但它们实际上是浮动汇率):
List = [4,5,6,7,8,9,10,11,12] #__len__ = 9
我需要通过off = 3来“延迟”(偏移)此列表(但这个数字,3,可能是变量),为第一个“off”值添加“0”,然后从“off + 1”开始“列表中的值为”0“:
OffsetList = [0,0,0,4,5,6,7,8,9] #__len__ = 9
我已经考虑过这两种可能的解决方案,但我对编程很陌生,我希望得到一个人的意见,无论是什么是最优化的解决方案,以及是否可以开发一个不同的解决方案可能比我想到的更好:
#SOLUTION 1
OffsetList = []
for _ in range(0,off):
OffsetList.append(0)
for k in range(0, len(List) - off):
OffsetList.append(List[k])
#SOLUTION 2
OffsetList = []
for _ in range(0,off):
OffsetList.append(0)
j = 0
while len(OffsetList) < len(List):
OffsetList.append(List[j])
j += 1
您认为哪一个更优化(快速,安全,稳定等),为什么?另外(我敢肯定),有没有比我想到的更好的解决方案?
答案 0 :(得分:3)
您可以使用列表切片:
>>> List = [4,5,6,7,8,9,10,11,12]
>>> off = 3
>>> OffsetList = [0]*len(List)
>>> OffsetList[off:] = List[:-off]
>>> OffsetList
[0, 0, 0, 4, 5, 6, 7, 8, 9]
答案 1 :(得分:2)
您可以将列表推导用于此类事情:
List = [4,5,6,7,8,9,10,11,12]
off = 3
OffsetList = [0 for x in xrange(off)] + List[:-off]
print OffsetList
答案 2 :(得分:2)
>>> l = [4,5,6,7,8,9,10,11,12]
>>> off = 3
>>> [0] * off + l[:-off]
[0, 0, 0, 4, 5, 6, 7, 8, 9]
答案 3 :(得分:1)
>>> List = [4,5,6,7,8,9,10,11,12]
>>> off = 3
>>> OffsetList = [0] * off + List[:-off]
>>> print (OffsetList)
>>> [0, 0, 0, 4, 5, 6, 7, 8, 9]
答案 4 :(得分:1)
最好不要在添加零时显式迭代列表
def prefix1(l, offset):
return l = [0] * offset + l
def prefix2(l, offset):
for _ in xrange(offset):
l.insert(0, 0)
return l
>>> %timeit prefix1([1,2,3,4,5], 500)
10000 loops, best of 3: 4.87 µs per loop
>>> %timeit prefix2([1,2,3,4,5], 500)
10000 loops, best of 3: 190 µs per loop
Sidenote :我正在使用iPython %timeit
魔法,它使用内置的timeit
module。您也可以直接调用模块的时间python -m timeit --setup 'n=50;l=[1,2,3,4,5]' 'l = [0] * n + l'
,但使用iPython可以使事情变得更容易。
通常,Python中的显式循环比列表推导慢,但这并不适用于所有内容,并不意味着您应该尝试将所有内容都写为列表推导。见this article。当看不清楚你想要什么时,我没有看到你为什么要使用while循环的原因,将n
元素添加到列表的开头。在这种情况下,我更喜欢准确说明l = [0] * offset + l
的意图的代码非常明确。
来自JoelCornett
的评论
import itertools
def prefix3(l, offset):
return list(itertools.chain([0] * offset, l))
def prefix4(l, offset):
return itertools.chain([0] * offset, l)
def prefix5(l, offset):
return itertools.chain(itertools.repeat(0, offset), l)
>>> %timeit prefix3([1,2,3,4,5], 500)
10000 loops, best of 3: 13 µs per loop
>>> %timeit prefix4([1,2,3,4,5], 500)
10000 loops, best of 3: 2.9 µs per loop
>>> %timeit prefix5([1,2,3,4,5], 500)
10000 loops, best of 3: 883 ns per loop
请注意,prefix5
以纳秒为单位测量,其他为微秒。
prefix3
和prefix4 & prefix5
之间的区别在于itertools.chain
返回迭代器(没有随机访问,您无法在其上调用len
)。因此,将其转换为prefix3
中的列表会产生开销。如果您只想迭代元素而不是按索引访问特定元素,则应使用prefix5
,否则prefix2
或prefix3
。