使用groupby结果修改列,同时忽略某些值

2024-03-28 13:32:22 发布

您现在位置:Python中文网/ 问答频道 /正文

我正在尝试使用Pandas修改一个带有groupby操作结果的大型数据集。 我需要的是找到数据组的最小值,同时忽略零,但返回相同的零,以防它是组中唯一的值。你知道吗

考虑以下虚拟数据:

>>> a=pd.DataFrame(dict(item_id=[1,1,1,2,2,2], pos_id=[3,7,7,7,7,7], target='T1 T2 T3 T1 T2 T3'.split(), val=[8,0,0,41,0,55]))
>>> a
   item_id  pos_id target  val
0        1       3     T1    8
1        1       7     T2    0
2        1       7     T3    0
3        2       7     T1   41
4        2       7     T2    0
5        2       7     T3   55

对于pos\u id==7和target==T2中的每个项目,我想得到整个组中最小的非零值(忽略target),并用这个替换它!你知道吗

所以,最后我想说:

   item_id  pos_id target  val
0        1       3     T1    8  <-- this row has the wrong pos_id and is ignored
1        1       7     T2    0  <-- this one maintains zero (all group has zeros)
2        1       7     T3    0
3        2       7     T1   41
4        2       7     T2   41  <-- this one gets the smallest of item_id group
5        2       7     T3   55

我试过这个:

>>> a.ix[(a.pos_id == 7) & (a.target == 'T2'), 'val'] = a.ix[a.pos_id == 7].groupby('item_id').val.min().values

但它不起作用,因为零没有被忽略。我不能简单地忽略它们,因为作业两边的系列会有不同的大小!你知道吗

>>> a.ix[(a.pos_id == 7) & (a.target == 'T2'), 'val'].size, a.ix[(a.pos_id == 7) & (a.val != 0)].groupby('item_id').val.min().values.size
(2, 1)

我还尝试在这些0中设置一个高值,因此第一个几乎可以成功:

>>> a.ix[(a.pos_id == 7) & (a.val == 0), 'val'] = 9999
>>> a
   item_id  pos_id target   val
0        1       3     T1     8
1        1       7     T2  9999
2        1       7     T3  9999
3        2       7     T1    41
4        2       7     T2  9999
5        2       7     T3    55

但是:

>>> a.ix[(a.pos_id == 7) & (a.target == 'T2'), 'val'] = a.ix[a.pos_id == 7].groupby('item_id').val.min().values
>>> a
   item_id  pos_id target   val
0        1       3     T1     8
1        1       7     T2  9999  <-- this one should maintain zero...
2        1       7     T3  9999
3        2       7     T1    41
4        2       7     T2    41  <-- this one works!
5        2       7     T3    55

但是现在我必须把不应该修改的值归零。。。 噢,这一定是个更好的办法!你知道吗

请问,我如何在一个简单的步骤中通过忽略一些值来设置groupvalue?另外,请考虑性能很重要,因为数据集只有几GB。。。你知道吗

谢谢你!你知道吗


Tags: 数据posidtargetvalminthisitem
1条回答
网友
1楼 · 发布于 2024-03-28 13:32:22

我认为可以使用带^{}的条件检查^{}值是否为0,然后输出为0,否则为^{},不带0值,而是带^{}apply

a=pd.DataFrame(dict(item_id=[1,1,1,2,2,2], 
                    pos_id=[3,7,7,7,7,7], 
                    target='T1 T2 T3 T1 T2 T3'.split(), 
                    val=[8,0,0,41,0,55]))
print a
   item_id  pos_id target  val
0        1       3     T1    8
1        1       7     T2    0
2        1       7     T3    0
3        2       7     T1   41
4        2       7     T2    0
5        2       7     T3   55

a.ix[(a.pos_id == 7) & (a.target == 'T2'), 'val'] = 
a.ix[a.pos_id == 7].groupby('item_id').val.transform(lambda x: np.where((x == 0).all(), 
                                                                        0, 
                                                                        x[x!=0].min()))
print a
   item_id  pos_id target  val
0        1       3     T1    8
1        1       7     T2    0
2        1       7     T3    0
3        2       7     T1   41
4        2       7     T2   41
5        2       7     T3   55

相关问题 更多 >