繁体   English   中英

Pandas:如果最后一个非零值 < 0:替换为 0

[英]Pandas: if last non-zero value < 0: replace with 0

我有一个 dataframe:

df = pd.DataFrame({'A': [1,2,-2,0,0], 'B': [0, 0, 0, 3, -2], 'C' : [0, 0, -2, 4, 0], 'D': [0, -3, 2, 1, -2]} ) 

Out: 
   A  B  C  D
0  1  0  0  0
1  2  0  0 -3
2 -2  0 -2  2
3  0  3  4  1
4  0 -2  0 -2

对于每一,如果最后一个非零值 < 0:用 0 替换它。

预期结果:


df_end = pd.DataFrame({'A': [1,2,0,0,0], 'B': [0, 0, 0, 3, 0], 'C' : [0, 0, -2, 4, 0], 'D': [0, -3, 2, 1, 0]} ) 
df_end

Out: 
   A  B  C  D
0  1  0  0  0
1  2  0  0 -3
2  0  0 -2  2
3  0  3  4  1
4  0  0  0  0

我已经解决了相反的问题(如果第一个非零值 < 0,则替换为 0):

df.where(df.gt(0).cummax(),0)

我现在需要它从底部查看表格。

#EDIT 正如评论中指出的那样, df.where(df.gt(0).cummax(),0) 将消除所有 - 值,直到第一个正数。 在我原来的 Dataframe 中,正值和负值总是交替的,所以 df.where(df.gt(0).cummax(),0) 有效。 我做了一个不好的例子dataframe。

让我们尝试iloc[::-1]恢复df

df[~df.iloc[::-1].gt(0).cummax()] = 0

Output:

   A  B  C  D
0  1  0  0  0
1  2  0  0 -3
2  0  0 -2  2
3  0  3  4  1
4  0  0  0  0

更新:正如@Ben.T 评论的那样,如果您有几个负面结局,上述内容会将它们全部变为零。 这将解决:

df = pd.DataFrame({'A': [1,2,-2,-1,0], 'B': [0, 0, 0, 3, -2], 'C' : [0, 0, -2, 4, 0], 'D': [0, -3, 2, 1, -2]} ) 

s = df.iloc[::-1]
df[s.lt(0).cumsum().eq(1) & (~s.gt(0).cummax())] = 0

Output:

   A  B  C  D
0  1  0  0  0
1  2  0  0 -3
2 -2  0 -2  2
3  0  3  4  1
4  0  0  0  0

这只会将最后一个负值替换为 0

s=np.sign(df).iloc[::-1].eq(-1).idxmax()
df.values[s,df.columns.get_indexer(s.index)]=0
df
   A  B  C  D
0  1  0  0  0
1  2  0  0 -3
2  0  0  0  2
3  0  3  4  1
4  0  0  0  0

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM