Pandas使用另一列中的值重命名/转置列

时间:2015-11-07 19:58:01

标签: python pandas dataframe

我不是大熊猫专家,所以我很难知道如何完成什么,我认为,这是一个非常简单的DataFrame操作。我有一个如下所示的DataFrame:

                       Id              appName       _RT      _count
0    ef9fdeed-a9ad-4680-b8e9-9e5e10ae2593      App1  0.003000       1
1    ef9fdeed-a9ad-4680-b8e9-9e5e10ae2593      App2  0.026000       1
2    ef9fdeed-a9ad-4680-b8e9-9e5e10ae2593      App3  0.029000       1
3    ef9fdeed-a9ad-4680-b8e9-9e5e10ae2593      App2  0.052000       2
4    ef9fdeed-a9ad-4680-b8e9-9e5e10ae2593      App2  0.070000       1
5    ef9fdeed-a9ad-4680-b8e9-9e5e10ae2593      App1  0.124000       2
6    f03eaf42-9080-43c8-a892-f910fa442ee6      App3  0.060000       1

我想要完成的是为_RT和_count创建appName的新列,如下所示:

                       Id              appName       App1_RT      App1_count   App2_RT  App2_count  App3_RT    App3_count
0    ef9fdeed-a9ad-4680-b8e9-9e5e10ae2593      App1  0.003000       1
1    ef9fdeed-a9ad-4680-b8e9-9e5e10ae2593      App2                           0.026000     1
2    ef9fdeed-a9ad-4680-b8e9-9e5e10ae2593      App3                                                 0.029000       1
3    ef9fdeed-a9ad-4680-b8e9-9e5e10ae2593      App2                           0.052000       2
4    ef9fdeed-a9ad-4680-b8e9-9e5e10ae2593      App2                           0.070000       1
5    ef9fdeed-a9ad-4680-b8e9-9e5e10ae2593      App1  0.124000       2
6    f03eaf42-9080-43c8-a892-f910fa442ee6      App3                                                0.060000       1

我的第一个想法是使用transpose(),但我觉得必须有其他方法来做到这一点。老实说,我只是在最好的方式上迷失了。任何帮助将不胜感激。谢谢。

1 个答案:

答案 0 :(得分:2)

df = df.set_index(['Id', 'appName'], append=True).unstack()
df.columns = ['{}{}'.format(name, id) for id, name in df.columns]

产量

            App1_RT  App2_RT  App3_RT  App1_count  App2_count  App3_count
  Id                                                                     
0 ef9fdeed    0.003      NaN      NaN           1         NaN         NaN
1 ef9fdeed      NaN    0.026      NaN         NaN           1         NaN
2 ef9fdeed      NaN      NaN    0.029         NaN         NaN           1
3 ef9fdeed      NaN    0.052      NaN         NaN           2         NaN
4 ef9fdeed      NaN    0.070      NaN         NaN           1         NaN
5 ef9fdeed    0.124      NaN      NaN           2         NaN         NaN
6 f03eaf42      NaN      NaN    0.060         NaN         NaN           1

为了便于阅读,Id被截断了。

请注意,appName列中的是所需DataFrame中的列名。 将值从列移动到列索引中可以分两步执行:

  1. 使用set_index

  2. 将值移动到索引中
  3. 使用unstack将索引级别值移动到列索引中。

  4. 完成后,您只需重命名列以将MultiIndex压缩为单个索引级别。这是通过重新分配给df.columns来完成的。请注意,您可能希望跳过该步骤,因为如果您需要根据appNamecountRT选择列,MultiIndex会在以后阶段提供richer structure which may be useful

    Id列也被放置在索引中,以“保护”它不被unstack操作拆分。看看我的意思最简单的方法就是看看 Python解释器中的df.set_index(['appName'], append=True).unstack()

    In [144]: df.set_index(['appName'], append=True).unstack()
    Out[144]: 
                   Id                        _RT               _count          
    appName      App1      App2      App3   App1   App2   App3   App1 App2 App3
    0        ef9fdeed       NaN       NaN  0.003    NaN    NaN      1  NaN  NaN
    1             NaN  ef9fdeed       NaN    NaN  0.026    NaN    NaN    1  NaN
    2             NaN       NaN  ef9fdeed    NaN    NaN  0.029    NaN  NaN    1
    3             NaN  ef9fdeed       NaN    NaN  0.052    NaN    NaN    2  NaN
    4             NaN  ef9fdeed       NaN    NaN  0.070    NaN    NaN    1  NaN
    5        ef9fdeed       NaN       NaN  0.124    NaN    NaN      2  NaN  NaN
    6             NaN       NaN  f03eaf42    NaN    NaN  0.060    NaN  NaN    1
    

    In [145]: df.set_index(['Id', 'appName'], append=True).unstack()
    Out[145]: 
                  _RT               _count          
    appName      App1   App2   App3   App1 App2 App3
      Id                                            
    0 ef9fdeed  0.003    NaN    NaN      1  NaN  NaN
    1 ef9fdeed    NaN  0.026    NaN    NaN    1  NaN
    2 ef9fdeed    NaN    NaN  0.029    NaN  NaN    1
    3 ef9fdeed    NaN  0.052    NaN    NaN    2  NaN
    4 ef9fdeed    NaN  0.070    NaN    NaN    1  NaN
    5 ef9fdeed  0.124    NaN    NaN      2  NaN  NaN
    6 f03eaf42    NaN    NaN  0.060    NaN  NaN    1