【问题标题】:How can I groupby a dataFrame whose columns names are tuples?如何按列名称为元组的数据框分组?
【发布时间】:2018-10-07 12:16:28
【问题描述】:

我有一个在 4 个循环内创建的数据帧。我不确定这是否是最好的方法,但经过长时间的研究,我只设法创建了一个以长度为 4 的元组作为列名的数据帧。我现在需要在元组中的 some 条目中对所有具有条件的列进行分组,而不是按顺序。这是我所拥有的示例:

import numpy as np
import pandas as pd
from collections import namedtuple

tuplekey = namedtuple("tuplekey", ["key1","key2","key3","key4"])

randomarray = np.random.rand(10)

list1 = []
for i in range(0,2):
    list2 = []
    for j in range(0,2):
        list3 = []
        for k in range(0,2):
            list4 = []
            for l in range(0,2):

                key = tuplekey('I'+str(i), 'J'+str(j), 'K'+str(k), 'L'+str(l))
                df1 = pd.DataFrame({key:[randomarray]})
                list4.append(df1)

            df2 = pd.concat(list4, axis=1)
            list3.append(df2)

        df3 = pd.concat(list3, axis=1)
        list2.append(df3)

    df4 = pd.concat(list2, axis=1)
    list1.append(df4)

df = pd.concat(list1, axis=1)

list(df.columns.values)

>>> [('I0', 'J0', 'K0', 'L0'),
 ('I0', 'J0', 'K0', 'L1'),
 ('I0', 'J0', 'K1', 'L0'),
 ('I0', 'J0', 'K1', 'L1'),
 ('I0', 'J1', 'K0', 'L0'),
 ('I0', 'J1', 'K0', 'L1'),
 ('I0', 'J1', 'K1', 'L0'),
 ('I0', 'J1', 'K1', 'L1'),
 ('I1', 'J0', 'K0', 'L0'),
 ('I1', 'J0', 'K0', 'L1'),
 ('I1', 'J0', 'K1', 'L0'),
 ('I1', 'J0', 'K1', 'L1'),
 ('I1', 'J1', 'K0', 'L0'),
 ('I1', 'J1', 'K0', 'L1'),
 ('I1', 'J1', 'K1', 'L0'),
 ('I1', 'J1', 'K1', 'L1')]

我现在需要按“I1”分组,然后按“K1”和“K2”分组。

我尝试过使用

group = df.groupby(["I1"])

但这会产生以下错误:

ValueError: 'I1' 的 Grouper 不是一维的

我知道这是错误的,因为我的列名是长度为 4 的元组,但我不知道怎么说

df.groupby(["I1",*,*,*])

每个 * 都是一个“通配符”。

我查找了该错误并发现 this answer 提供了解决方案。因为我有 4 个键而不是 2 个,所以我尝试了:

df1.rename(columns={ key[3] : {key[2] : { key[0]:key[1] }}}, inplace=True)

但这给出了错误

TypeError: unhashable type: 'dict'

那么在这种情况下,我如何按“I1”(以及进一步按“I1”和“K1”等)分组?

最后我想补充一点,我不需要dataFrame的名称是一个元组,我只需要保留每个循环的信息。我正在尝试使用 Pandas,因为稍后我想使用 seaborn 绘制一些数据帧。如果您认为有更好的方法来构建这个 dataFrame,以便稍后我可以更轻松地对其进行操作,请不要犹豫告诉我·

【问题讨论】:

  • 你试过df.groupby([["I1"]])而不是df.groupby(["I1"])。你也知道你创建了一个MultiIndex 数据框,只是问它没有写在任何地方?
  • @Ben.T df.groupby([["I1"]]) 给出ValueError: Grouper and axis must be same length。不,我绝对不知道我创建了一个 MultiIndex 数据帧。我现在将在 MultiIndex 数据帧中寻找解决方案!感谢您的意见!
  • 好的,它对我有用,不知道为什么(我复制了你的代码)。所以如果你只想要16个根据你的列表命名的常规列,有一个更简单的方法,我会写一个答案

标签: python pandas pandas-groupby


【解决方案1】:

要轻松创建一个包含 16 列并以元组命名的 DF,您可以:

import pandas as pd
import itertools
list_ind = [['I0', 'I1'], ['J0', 'J1'], ['K0', 'K1'], ['L0', 'L1']]
list_col = list(itertools.product(*list_ind)) # all permutations possible
df1 = pd.DataFrame(columns = list_col )

请注意,DF 是空的。

如果你想以groupby 元组包含I1 为例,你可以这样做:

list_I1 = [tup for tup in df1.columns if tup[0] == 'I1']
group = df1.groupby(list_I1)

这是你要找的吗?

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-04-01
    • 2017-04-16
    • 2022-01-02
    • 1970-01-01
    • 1970-01-01
    • 2021-11-20
    相关资源
    最近更新 更多