我有一个带有True / False值的Pandas系列,我需要计算一个与前一个值相同的值的频率。
每当值发生变化时,计数应重新开始为1。
pd.Series([True, False, False, False, True, True, False])
0 True --> 1
1 False --> 1
2 False --> 2
3 False --> 3
4 True --> 1
5 True --> 2
6 False --> 1
dtype: bool
我尝试了shift()和cumsum()的各种组合,但没有成功。
任何提示?
啤酒
答案 0 :(得分:3)
您可以按比较shift
ed值和cumsum
的连续值创建群组,并将其用于cumcount
:
cd destination folder
lcd source folder path
prompt
mput *.*
详情:
s = pd.Series([True, False, False, False, True, True, False])
s1 = s.groupby(s.ne(s.shift()).cumsum()).cumcount().add(1)
print (s1)
0 1
1 1
2 2
3 3
4 1
5 2
6 1
dtype: int64
另一个解决方案是分别计算print (s.ne(s.shift()).cumsum())
0 1
1 2
2 2
3 2
4 3
5 3
6 4
dtype: int32
和True
,然后求和:
False
详情:
cm1 = s.cumsum()
s1 = cm1-cm1.where(~s).ffill().fillna(0)
cm2 = (~s).cumsum()
s2 = cm2-cm2.where(s).ffill().fillna(0)
s3 = s1.add(s2).astype(int)
print (s3)
0 1
1 1
2 2
3 3
4 1
5 2
6 1
dtype: int32
<强>计时强>:
print (s1)
0 1.0
1 0.0
2 0.0
3 0.0
4 1.0
5 2.0
6 0.0
dtype: float64
print (s2)
0 0.0
1 1.0
2 2.0
3 3.0
4 0.0
5 0.0
6 1.0
dtype: float64
np.random.seed(2018)
N = 1000000
s = pd.Series(np.random.choice([True, False], N))
#print (s)
def jez1(s):
return s.groupby(s.ne(s.shift()).cumsum()).cumcount().add(1)
def jez2(s):
cm1 = s.cumsum()
s1 = cm1-cm1.where(~s).ffill().fillna(0)
cm2 = (~s).cumsum()
s2 = cm2-cm2.where(s).ffill().fillna(0)
return s1.add(s2).astype(int)