【问题标题】:Is there a way to sum over an index level in a dataframe while preserving index levels that are repeated?有没有办法对数据框中的索引级别求和,同时保留重复的索引级别?
【发布时间】:2020-04-14 16:51:58
【问题描述】:

我有一个看起来像这样的数据框:

                     2000 2001 2002 2003
Area Item Unit Code  
A    X    j    00    val  val  val  val
A    Y    k    01    val  val  val  val
A    Z    k    10    val  val  val  val
B    X    j    00    val  val  val  val
B    Y    k    01    val  val  val  val
B    Z    k    10    val  val  val  val

我想对这些区域求和以生成如下所示的 DataFrame:

                     2000 2001 2002 2003
Area Item Unit Code  
C    X    j    00    val  val  val  val
C    Y    k    01    val  val  val  val
C    Z    k    10    val  val  val  val

如果我使用df = df.sum(level = "Item"),则索引的其余部分将被删除并且我得到(这是我所期望的):

     2000 2001 2002 2003
X    val  val  val  val
Y    val  val  val  val
Z    val  val  val  val

我可以使用df = pd.concat([df], keys = ["C"], names = ["Area"]) 来解决“区域”方面的问题,但这对索引的其余部分没有帮助。

我找不到在保留 DataFrame 结构的同时对区域数据求和的方法。

我的实际数据框大于我给出的示例(Area 值转到 A B C ... ZY ZZ 等)。

【问题讨论】:

  • 请分享一个可重现的问题。给出一个实际值的样本,而不是val
  • 这是一个很好的问题。值得同样好的答案。很抱歉我帮不上忙

标签: python pandas dataframe python-3.7 multi-index


【解决方案1】:

首先在没有第一个Area的情况下由所有级别使用sum,然后创建由C填充的新列,使用append=True添加到索引DataFrame.set_index,最后一个DataFrame.reorder_levels作为该列的第一个位置:

print (df)
                     2000  2001  2002  2003
Area Item Unit Code                        
A    X    j    0       10    10    10    10
     Y    k    1       10    10    10    10
     Z    k    10      10    10    10    10
B    X    j    0       10    10    10    10
     Y    k    1       10    10    10    10
     Z    k    10      10    10    10    10


df1 = (df.sum(level = ["Item","Unit","Code"])
         .assign(Area = 'C')
         .set_index('Area', append=True)
         .reorder_levels([3,0,1,2]))
print (df1)
                     2000  2001  2002  2003
Area Item Unit Code                        
C    X    j    0       20    20    20    20
     Y    k    1       20    20    20    20
     Z    k    10      20    20    20    20

另一种解决方案:

df1 = (df.sum(level = ["Item","Unit","Code"])
         .assign(Area = 'C')
         .reset_index()
         .set_index(["Area", "Item","Unit","Code"]))
print (df1)
                     2000  2001  2002  2003
Area Item Unit Code                        
C    X    j    0       20    20    20    20
     Y    k    1       20    20    20    20
     Z    k    10      20    20    20    20

【讨论】:

    猜你喜欢
    • 2017-09-21
    • 2020-01-05
    • 1970-01-01
    • 2020-09-06
    • 2013-12-04
    • 2018-08-24
    • 2018-04-20
    • 2014-08-09
    • 1970-01-01
    相关资源
    最近更新 更多