pandas groupby连续的数字和它后面的一行,然后检查每个组的列的第一个值,并创建一个新列

vmdwslir  于 5个月前  发布在  其他
关注(0)|答案(2)|浏览(38)

这是我的博客:

df = pd.DataFrame(
    {
        'a': [0, 0, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 0, 0, 1, 1, 0],
        'b': [1, -1, -1, -1, 1, -1, 1, 1, -1, 1, 1, -1, 1, 1, -1, 1, 1]    
    }
)

字符串
这是我想要的输出。我想创建列c

a  b  c
0   0  1  0
1   0 -1  0
2   1 -1  0
3   1 -1  0
4   1  1  1
5   1 -1  1
6   0  1  0
7   0  1  0
8   0 -1  0
9   1  1  1
10  1  1  1
11  1 -1  1
12  0  1  0
13  0  1  0
14  1 -1  0
15  1 -1  1
16  0  1  0


这基本上是这个post的扩展。下面突出显示的行总结了需要完成的方式。


的数据
首先,在列a中,组是由1s的条纹和条纹结束后的一行创建的。列a中突出显示的行是这些组。此步骤的解决方案是here
现在我需要检查a中每个组的b列。为每个组找到b中的第一个值1。然后在此之前的任何值都变为0。这就是如何创建c列的。
例如,对于a中的第一个组,列b为1的第一个值是行号4。该组中以前的值变为0。结果是列c中的第一个突出显示的组。
请注意,如果对于一个组,b中的所有值都不是1,则c中的相应组将变为全0。
这是我尝试过的,但我找不到完整的解决方案:

g = df.loc[::-1, 'a'].eq(0).cumsum()
x = df.groupby(g).filter(lambda x: x.b.iloc[0] == 1)

ocebsuys

ocebsuys1#

使用df['b'].eq(1)上的groupby.cummax和从分组器导出的中间掩码的链接答案的变体:

m = df.loc[::-1, 'a'].eq(0)
g = m.cumsum()

df['c'] = np.where(df['b'].eq(1).groupby(g).cummax() & ~m, 1, 0)

字符串
输出和中间体:

a  b  c      m     ~m  cummax  cummax&~m
0   0  1  0   True  False    True      False
1   0 -1  0   True  False   False      False
2   1 -1  0  False   True   False      False
3   1 -1  0  False   True   False      False
4   1  1  1  False   True    True       True
5   1 -1  1  False   True    True       True
6   0  1  0   True  False    True      False
7   0  1  0   True  False    True      False
8   0 -1  0   True  False   False      False
9   1  1  1  False   True    True       True
10  1  1  1  False   True    True       True
11  1 -1  1  False   True    True       True
12  0  1  0   True  False    True      False
13  0  1  0   True  False    True      False
14  1 -1  0  False   True   False      False
15  1  1  1  False   True    True       True
16  0  1  0   True  False    True      False

eoxn13cs

eoxn13cs2#

通过GroupBy.cummax创建掩码并与Series.duplicated链接,将0,1转换为整数:

g = df.loc[::-1, 'a'].eq(0).cumsum()
df['c'] = (df['b'].eq(1).groupby(g).cummax() & g.duplicated()).astype(int)
print (df)
    a  b  c
0   0  1  0
1   0 -1  0
2   1 -1  0
3   1 -1  0
4   1  1  1
5   1 -1  1
6   0  1  0
7   0  1  0
8   0 -1  0
9   1  1  1
10  1  1  1
11  1 -1  1
12  0  1  0
13  0  1  0
14  1 -1  0
15  1  1  1
16  0  1  0

字符串

相关问题