不同长度的pandas groupby元组-ValueError:在通过级别中找不到值:MultiIndex

Posted

技术标签:

【中文标题】不同长度的pandas groupby元组-ValueError:在通过级别中找不到值:MultiIndex【英文标题】:pandas groupby tuple of different length - ValueError: Values not found in passed level: MultiIndex 【发布时间】:2021-05-31 07:19:05 【问题描述】:

编辑:找到并发布的原始错误消息的示例 DataFrame。

(正如我刚刚认识到的那样,只有在元组具有一定长度时才会出现错误。现在已经修改了示例。)

原文:

我需要按不同长度的元组进行分组。

对于分组,我应用了一个 summary_function。

import pandas as pd

def summary_function(df):
    value_mean = df['value'].mean()
    df1 = pd.DataFrame('value_mean':[value_mean]
                        )
    return df1

tuple_list = [(1,2,1,1,1,1,1,1,1,1,1,1,1),(2,3,1,1,1,1,1,1,1,1,1,1,1), \
          (1,2,1,1,1,1,1,1,1,1,1,1,1), \
          (2,3,4,4,4,4,4,4,4,4,4,4,4,4,4,1,1,1,1,1,1,1,1,1,1,1)]

value = [1,2,3,4]
letter = list('abab')

df = pd.DataFrame('letter':letter, 'tuple':tuple_list, 'value':value)
df

>    letter     tuple                                           value
>0  a       (1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1)             1
>1  b       (2, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1)             2
>2  a       (1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1)             3
>3  b       (2, 3, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, ...   4

如果我使用直接 mean() 函数,结果是预期的:

df.groupby(['letter','tuple']).mean()

>                                                       value
>letter     tuple   
>a       (1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1)        2
>b       (2, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1)        2
>        (2, 3, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, ...)   4

但是如果我应用这个功能。 (我需要使用,因为我有几十个摘要)使用简单时元组是空的

df.groupby(['letter','tuple']).apply(lambda x:summary_function(x))

我得到一个 ValueError:

>ValueError: Values not found in passed level: MultiIndex([(2, 3, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4)],
       )

如果能获得一些关于如何解决这个问题的想法会很棒。

【问题讨论】:

将此return df1 更改为return value_mean 这应该可以完成工作。 不返回 apply 中的数据帧,只返回单个标量。 @Quang Hoang 真正的函数不是返回一个只有一个单元格但有 2 打列的数据框。因此,仅返回标量不是一种选择。当然,我可以返回 2 打参数(标量、数组、列表)。但我不认为这些东西会通过 groupby 很好地粘贴在一起。 【参考方案1】:

在你的情况下,不要返回数据框,返回系列。

当您返回系列时,Pandas 会水平对齐系列。例如:

def summary_function(df):
    return df['value'].agg(['min','mean','max'])

df.groupby(['letter','tuple']).apply(summary_function)

输出:

value                                                      min  mean  max
letter tuple                                                             
a      (1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1)             1.0   2.0  3.0
b      (2, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1)             2.0   2.0  2.0
       (2, 3, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 1...  4.0   4.0  4.0

【讨论】:

解决方案更加简单。我刚刚用 pd.Series 替换了 pd.DataFrame。你的回答启发了我这个解决方案。非常感谢!【参考方案2】:

更短的解决方案是将“pd.DataFrame”替换为“pd.Series”。

def summary_function(df):
    value_mean = df['value'].mean()
    df1 = pd.Series('value_mean':[value_mean]
                    )

(灵感来自 Quang Hoang 的回答)

【讨论】:

以上是关于不同长度的pandas groupby元组-ValueError:在通过级别中找不到值:MultiIndex的主要内容,如果未能解决你的问题,请参考以下文章

修复Pandas中的Groupby长度

Pandas - 使用 groupby 创建最常用词的元组

Pandas:groupby A 列并从其他列创建元组列表?

Pandas Groupby 列并获得频率为 0

Pandas实现groupby分组聚合后不同列数据统计

python--pandas分组聚合