查找更改前连续元素的数量

时间:2016-06-11 17:17:31

标签: python list

例如,如果我有列表

a = [1,1,1,2,2]
b = [1,1,2,2,2]
c = [2,1,1,1,1]

我想获得列表中第一个元素的最长条纹,所以例如a将给出3,b将给出2而c将给出1.我知道我可以创建一个while循环并以这种方式计算条纹,但我想知道是否有更优雅的方法来做到这一点?

4 个答案:

答案 0 :(得分:6)

你可以这样做:

numStreak = ([a[0] == n for n in a]+[False]).index(False)

(这也确保如果所有元素都像第一个元素一样,索引会返回正确的值)

更新:更高效(但不太优雅?)版本

from itertools import takewhile
len([1 for _ in takewhile(lambda x:x==a[0], a)])

或更好一点(更新2)@ vaultah的建议:

sum(1 for _ in takewhile(lambda x:x==a[0], a))

答案 1 :(得分:3)

您可以使用groupby并汇总第一组中每个项目的数量:

a = [1,1,1,2,2]
b = [1,1,2,2,2]
c = [2,1,1,1,1]

from itertools import groupby

for l in [a,b,c]:
    print(sum( 1  for _ in next(groupby(l), [[], []],)[1]))

或者使用takewhile:

from itertools import takewhile

for l in [a, b, c]:
     print(sum((1 for _ in takewhile(lambda x: x == l[0], l))))

如果您的数据始终是 groupby 中的列表,元组等..您可以检查 falsey 值,而不是在{{1}中设置默认值}:

next(..

答案 2 :(得分:1)

一条公路班轮?瞄准......

a = [5,5,5,5,8]
list(np.ediff1d(a)).count(0)+1
>>> 4

答案 3 :(得分:0)

你可以使用numpy:

>>> import numpy as np
>>> a = [1,1,1,2,2]
>>> b = [1,1,2,2,2]
>>> c = [2,1,1,1,1]
>>> def runs(data):
...    return np.split(data, np.where(np.diff(data) != 0)[0]+1)
... 
>>> for e in a,b,c:
...    runs(np.array(e))
... 
[array([1, 1, 1]), array([2, 2])]
[array([1, 1]), array([2, 2, 2])]
[array([2]), array([1, 1, 1, 1])]

然后只需要第一次运行的长度:

>>> for e in a,b,c:
...    len(runs(np.array(e))[0])
... 
3
2
1

或者,在Python中,只需使用while循环:

>>> def r(a):
...    i=1
...    while a[0]==a[i]: i+=1
...    return i
... 
>>> r(a)
3
>>> r(b)
2
>>> r(c)
1