我有一个pandas数据框,其中的一列描述了整数时间索引,我想添加一列来存储行是否是条纹的一部分以及条纹的长度。例如,给定time
列,我想像这样计算streak
列
time streak
0 3
1 3
2 3
4 2
5 2
5 2
9 1
11 1
11 1
由于索引0,1,2是连续的,因此前三行是三连胜的一部分。由于索引4,5也是连续的,因此以下三行的连胜数为2;重复索引5,但这在确定条纹的长度时不应该计算在内。最后,最后三行与其他任何行都不连续,因此它们的条纹为1。请注意,有时多于一行的行可以具有相同的time
。我需要以时间单位计算条纹的长度,以便多个条目不会影响条纹的长度,并且具有相同时间索引的行具有相同的条纹长度。请记住,其他列(未显示)存储在数据框中。
我如何获得价值?我尝试使用groupby
,shift
和类似的功能,但并没有走得太远。
编辑:对不起,我忘记指定有时可以重复time
索引了。为了解决这个问题,我扩展了这个问题。
答案 0 :(得分:3)
使用diff
查找是否继续(等于1),然后使用条件匹配的cumsum
,然后使用groupby
+ transform
{{1 }}
szie
答案 1 :(得分:2)
与Wen的答案非常相似,只是使用[s, h, .]
,我觉得这更可笑了。
value_counts
编辑:这是解决可能出现重复时间的新案例的解决方案。请注意,我们正在使用time = pd.Series([0, 1, 2, 4, 5, 9, 11])
# Give each row a streak id by incrementing whenever the difference isn't 1
streak = (time.diff() != 1).cumsum()
# Maps each id to the number of times the id occurs
result = streak.map(streak.value_counts())
print(result)
Out:
0 3
1 3
2 3
3 2
4 2
5 1
6 1
查找新条纹;这是基于以下假设:时间是(现在不一定严格)在增加整数。可能的重复只是意味着我们必须diff > 1
才能计算出映射的条纹ID数。
drop_duplicates