当前位置: 首页 > 知识库问答 >
问题:

熊猫:如何使用多索引运行支点?

米子轩
2023-03-14

我想在pandasDataFrame上运行一个pivot,索引是两列,而不是一列。例如,一个字段表示年份,一个字段表示月份,一个显示“项目1”和“项目2”的“项目”字段以及一个带有数值的“值”字段。我希望索引是年-月。

我唯一能做到这一点的方法是将这两个字段合并成一个字段,然后再将它们分开。有更好的办法吗?

下面复制了最少的代码。谢谢!

PS是的,我知道还有其他关于“pivot”和“multi-index”关键字的问题,但我不明白他们是否/如何帮助我解决这个问题。

import pandas as pd
import numpy as np

df= pd.DataFrame()
month = np.arange(1, 13)
values1 = np.random.randint(0, 100, 12)
values2 = np.random.randint(200, 300, 12)


df['month'] = np.hstack((month, month))
df['year'] = 2004
df['value'] = np.hstack((values1, values2))
df['item'] = np.hstack((np.repeat('item 1', 12), np.repeat('item 2', 12)))

# This doesn't work: 
# ValueError: Wrong number of items passed 24, placement implies 2
# mypiv = df.pivot(['year', 'month'], 'item', 'value')

# This doesn't work, either:
# df.set_index(['year', 'month'], inplace=True)
# ValueError: cannot label index with a null key
# mypiv = df.pivot(columns='item', values='value')

# This below works but is not ideal: 
# I have to first concatenate then separate the fields I need
df['new field'] = df['year'] * 100 + df['month']

mypiv = df.pivot('new field', 'item', 'value').reset_index()
mypiv['year'] = mypiv['new field'].apply( lambda x: int(x) / 100)  
mypiv['month'] = mypiv['new field'] % 100

共有3个答案

邵星河
2023-03-14

以下几点对我很有用:

mypiv = df.pivot(index=['year','month'],columns='item')[['values1','values2']]
罗浩然
2023-03-14

我相信,如果您在多重索引中包含,那么您可以取消堆叠:

df.set_index(['year', 'month', 'item']).unstack(level=-1)

这就产生了:

                value      
item       item 1 item 2
year month              
2004 1         21    277
     2         43    244
     3         12    262
     4         80    201
     5         22    287
     6         52    284
     7         90    249
     8         14    229
     9         52    205
     10        76    207
     11        88    259
     12        90    200

它比使用pivot\u table快一点,与使用groupby的速度大致相同或稍慢一点。

谢旻
2023-03-14

您可以分组,然后卸载。

>>> df.groupby(['year', 'month', 'item'])['value'].sum().unstack('item')
item        item 1  item 2
year month                
2004 1          33     250
     2          44     224
     3          41     268
     4          29     232
     5          57     252
     6          61     255
     7          28     254
     8          15     229
     9          29     258
     10         49     207
     11         36     254
     12         23     209

或者使用pivot_table

>>> df.pivot_table(
        values='value', 
        index=['year', 'month'], 
        columns='item', 
        aggfunc=np.sum)
item        item 1  item 2
year month                
2004 1          33     250
     2          44     224
     3          41     268
     4          29     232
     5          57     252
     6          61     255
     7          28     254
     8          15     229
     9          29     258
     10         49     207
     11         36     254
     12         23     209
 类似资料:
  • 问题内容: 因此,我了解到可以使用DataFrame.groupby而不用使用MultiIndex进行子采样/横截面。 另一方面,当我在DataFrame上具有MultiIndex时,仍然需要使用DataFrame.groupby进行子采样/横截面。 那么,除了在打印时非常有用和漂亮地显示层次结构之外,MultiIndex有什么好处? 问题答案: 在pandas 0.4版本中引入了分级索引(也称为

  • 问题内容: 我有一个带有列“ A”和“ B”的多索引数据框。 有没有一种方法可以通过在多索引的一列上进行过滤而不选择将索引重新设置为单列索引来选择行? 例如。 问题答案: 一种方法是使用Index方法: 在0.13,你就可以使用与参数: 注意:如果这是列MultiIndex而不是索引,则可以使用相同的技术:

  • 问题内容: 所以我有一个像这样的DataFrame: 我们可以像这样对它进行布尔索引 我们还可以通过行标签将其切片,如下所示: 我想同时执行这两个操作(因此,避免只做行标签过滤器而不必要地复制)。我将如何去做? 我要寻找的伪代码: 问题答案: 您几乎拥有它:

  • 我正在使用迭代代码遍历具有多索引的大数据帧。结果是一个具有多索引的系列。经过一些分析后,事实证明,大部分时间都花在获取序列的单元格值上,因此我想使用 Series.at 函数,因为它要快得多。不幸的是,我没有在熊猫文档中找到任何关于多索引的内容。 这是一个简单的代码: 我曾尝试过s.at[(“酒吧”、“一家”)],s.at[“酒吧”,“一家”),但没有这些作品。 有人知道如何在这种情况下使用.at

  • 问题内容: 我这样制作数据框。 我想通过使用一些熊猫方法将索引转换为此(例如set_index,stack 、、) 我怎样才能做到这一点? 问题答案: 我认为你需要与重塑,然后交换在水平由列由去年的排序列: 用另一种解决方案和:

  • 当我将函数应用于Groupby对象的多个列时,Pandas会抛出一个Future Warning。它建议使用列表作为索引,而不是元组。一个人会怎么做?