【问题标题】:what is the difference between with or without .loc when using groupby + transform in Pandas在 Pandas 中使用 groupby + transform 时有或没有 .loc 有什么区别
【发布时间】:2018-06-05 03:28:32
【问题描述】:

我是 python 新手。这是我的问题,这对我来说真的很奇怪。

一个简单的数据框如下所示:

a1=pd.DataFrame({'Hash':[1,1,2,2,2,3,4,4],
                 'Card':[1,1,2,2,3,3,4,4]})

我需要对a1进行Hash分组,计算每组有多少行,然后在a1中加一列表示行号。所以,我想使用 groupby + transform。

当我使用时:

a1['CustomerCount']=a1.groupby(['Hash']).transform(lambda x: x.shape[0])

结果正确:

   Card  Hash  CustomerCount
0     1     1              2
1     1     1              2
2     2     2              3
3     2     2              3
4     3     2              3
5     3     3              1
6     4     4              2
7     4     4              2

但是当我使用时:

a1.loc[:,'CustomerCount']=a1.groupby(['Hash']).transform(lambda x: x.shape[0])

结果是:

   Card  Hash  CustomerCount
0     1     1            NaN
1     1     1            NaN
2     2     2            NaN
3     2     2            NaN
4     3     2            NaN
5     3     3            NaN
6     4     4            NaN
7     4     4            NaN

那么,为什么会这样呢?

据我所知,loc 和 iloc(如 a1.loc[:,'CustomerCount'])总比没有好(如 a1['CustomerCount']),因此通常建议使用 loc 和 iloc。但是为什么会这样呢?

另外,我已经多次尝试使用 loc 和 iloc 来在一个数据框中生成一个新列。他们通常工作。那么这和groupby + transform有关系吗?

【问题讨论】:

    标签: python pandas pandas-groupby transform pandas-loc


    【解决方案1】:

    不同之处在于loc 处理将DataFrame 对象分配给单个列的方式。当您为DataFrame 分配Card 的列时,它试图排列索引和列名。列没有排列,你得到了NaNs。通过直接列访问分配时,它确定它是一列对另一列,然后就这样做了。

    减少到一列

    您可以通过将groupby 操作的结果减少到仅一列来解决此问题,从而便于解决。

    a1.loc[:,'CustomerCount'] = a1.groupby(['Hash']).Card.transform('size')
    a1
    
       Hash  Card  CustomerCount
    0     1     1              2
    1     1     1              2
    2     2     2              3
    3     2     2              3
    4     2     3              3
    5     3     3              1
    6     4     4              2
    7     4     4              2
    

    重命名列

    不要真的这样做,其他答案要简单得多

    a1.loc[:, 'CustomerCount'] = a1.groupby('Hash').transform(len).rename(
        columns={'Card': 'CustomerCount'})
    a1
    

    pd.factorizenp.bincount

    我实际上会做什么

    f, u = pd.factorize(a1.Hash)
    a1['CustomerCount'] = np.bincount(f)[f]
    a1
    

    或者内联复制

    a1.assign(CustomerCount=(lambda f: np.bincount(f)[f])(pd.factorize(a1.Hash)[0]))
    
       Hash  Card  CustomerCount
    0     1     1              2
    1     1     1              2
    2     2     2              3
    3     2     2              3
    4     2     3              3
    5     3     3              1
    6     4     4              2
    7     4     4              2
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2011-03-18
      • 1970-01-01
      • 2018-07-02
      • 1970-01-01
      • 2014-02-27
      • 2014-07-13
      • 1970-01-01
      • 2013-08-22
      相关资源
      最近更新 更多