有没有办法在保留重复的索引级别的同时对数据框中的索引级别求和?

Is there a way to sum over an index level in a dataframe while preserving index levels that are repeated?

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

                     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"]) 来解决 "Area" 方面的问题,但这对索引的其余部分没有帮助。

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

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

首先在没有第一个 Area 的所有级别上使用 sum,然后创建由 C 填充的新列,通过 DataFrame.set_index with append=True and last 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