我有一个DataFrame,在列中有许多缺失的值,我希望通过分组:
import pandas as pd
import numpy as np
df = pd.DataFrame({'a': ['1', '2', '3'], 'b': ['4', np.NaN, '6']})
In [4]: df.groupby('b').groups
Out[4]: {'4': [0], '6': [2]}
看到Pandas已经删除了具有NaN目标值的行。(我想包括这些行!)
因为我需要很多这样的操作(许多cols有缺失的值),并且使用比中位数更复杂的函数(通常是随机森林),所以我希望避免编写过于复杂的代码段。
有什么建议吗?我应该写一个函数还是有简单的解决方案?
我已经回答了这个问题,但由于某些原因,答案被转换为评论。然而,这是最有效的解决方案:
不能在组中包含(和传播)nan是相当严重的。引用R是没有说服力的,因为这种行为与许多其他事情不一致。不管怎样,虚拟黑客也很糟糕。但是,如果组中存在nan,则组的大小(包括nan)和计数(忽略nan)会有所不同。
dfgrouped = df.groupby(['b']).a.agg(['sum','size','count'])
dfgrouped['sum'][dfgrouped['size']!=dfgrouped['count']] = None
当这些值不同时,您可以将该组的聚合函数结果的值设置为None。
我不能给M. Kiewisch添加评论,因为我没有足够的声誉点(只有41点,但需要超过50点来评论)。
不管怎样,只是想指出M. Kiewisch解决方案并不管用,可能需要更多的调整。举个例子
>>> df = pd.DataFrame({'a': [1, 2, 3, 5], 'b': [4, np.NaN, 6, 4]})
>>> df
a b
0 1 4.0
1 2 NaN
2 3 6.0
3 5 4.0
>>> df.groupby(['b']).sum()
a
b
4.0 6
6.0 3
>>> df.astype(str).groupby(['b']).sum()
a
b
4.0 15
6.0 3
nan 2
这表明对于b=4.0组,对应的值是15而不是6。这里只是将1和5作为字符串连接起来,而不是作为数字相加。
我已经回答了这个问题,但由于某些原因,答案被转换为评论。然而,这是最有效的解决方案:
不能在组中包含(和传播)nan是相当严重的。引用R是没有说服力的,因为这种行为与许多其他事情不一致。不管怎样,虚拟黑客也很糟糕。但是,如果组中存在nan,则组的大小(包括nan)和计数(忽略nan)会有所不同。
dfgrouped = df.groupby(['b']).a.agg(['sum','size','count'])
dfgrouped['sum'][dfgrouped['size']!=dfgrouped['count']] = None
当这些值不同时,您可以将该组的聚合函数结果的值设置为None。
在文档的缺失数据部分提到了这一点:
“GroupBy”中的NA组被自动排除。这个行为与R一致
一个解决方法是在执行groupby(例如-1)之前使用占位符:
In [11]: df.fillna(-1)
Out[11]:
a b
0 1 4
1 2 -1
2 3 6
In [12]: df.fillna(-1).groupby('b').sum()
Out[12]:
a
b
-1 2
4 1
6 3
也就是说,这感觉很糟糕……也许应该有一个选项,包括NaN在groupby(见这个github问题-它使用相同的占位符黑客)。
然而,正如另一个答案所描述的,“从熊猫1.1中,你可以更好地控制这种行为,现在允许在石斑鱼中使用dropna=False的NA值”