在 Pandas 数据框中的不同列上使用 lambda if 条件
Posted
技术标签:
【中文标题】在 Pandas 数据框中的不同列上使用 lambda if 条件【英文标题】:Using lambda if condition on different columns in Pandas dataframe 【发布时间】:2016-09-23 09:48:46 【问题描述】:我有简单的数据框:
import pandas as pd
frame = pd.DataFrame(np.random.randn(4, 3), columns=list('abc'))
例如:
a b c
0 -0.813530 -1.291862 1.330320
1 -1.066475 0.624504 1.690770
2 1.330330 -0.675750 -1.123389
3 0.400109 -1.224936 -1.704173
然后我想创建列“d”,如果 c 为正,则包含来自“c”的值。来自“b”的其他值。
我正在尝试:
frame['d']=frame.apply(lambda x: frame['c'] if frame['c']>0 else frame['b'],axis=0)
但是得到“ValueError:('一个Series的真值是模棱两可的。使用a.empty, a.bool(), a.item(), a.any() or a.all().', '发生在索引 a')
我试图谷歌如何解决这个问题,但没有成功。请问有什么建议吗?
【问题讨论】:
lambda x: ...
因为它需要一个不用于逻辑的参数x
.....
frame['c']>0
在列 c 中生成一系列大于 0 的值,然后尝试使用它的布尔值而不是 x['c']>0
将特定单元格处的值与0 并返回一个布尔值。
【参考方案1】:
这就是你想要的吗?
In [300]: frame[['b','c']].apply(lambda x: x['c'] if x['c']>0 else x['b'], axis=1)
Out[300]:
0 -1.099891
1 0.582815
2 0.901591
3 0.900856
dtype: float64
【讨论】:
【参考方案2】:解决方案
使用矢量化方法
frame['d'] = frame.b + (frame.c > 0) * (frame.c - frame.b)
说明
这是从总和得出的
(frame.c > 0) * frame.c # frame.c if positive
加号
(frame.c <= 0) * frame.b # frame.b if c is not positive
然而
(frame.c <=0 )
等价于
(1 - frame.c > 0)
合并后得到
frame['d'] = frame.b + (frame.c > 0) * (frame.c - frame.b)
【讨论】:
以上是关于在 Pandas 数据框中的不同列上使用 lambda if 条件的主要内容,如果未能解决你的问题,请参考以下文章
使用 Pandas 将数据框中的 Python 对象列转换为没有日期的时间