用两列在大熊猫分组中排序

时间:2020-04-20 21:28:30

标签: python pandas

我正在尝试将数据帧分为两列,并避免使用'sort = False'进行默认排序。但是,我无法实现这一目标。

这是简化的示例

df = pd.DataFrame([
        ['zebra', 1, 10],
        ['zebra', 2, 10],
        ['apple', 3, 20],
        ['apple', 4, 20],
    ],
    columns=['ColA','ColB','ColC'])

df因此是

    ColA  ColB  ColC
0  zebra     1    10
1  zebra     2    10
2  apple     3    20
3  apple     4    20

我正在使用pandas(1.0.3)groupby并禁用键的排序

df_agg = df.groupby(by=['ColA','ColB'], sort = False)

df_agg.groups

结果

{('apple', 3): Int64Index([2], dtype='int64'),
 ('apple', 4): Int64Index([3], dtype='int64'),
 ('zebra', 1): Int64Index([0], dtype='int64'),
 ('zebra', 2): Int64Index([1], dtype='int64')}

与“ sort = True”(默认)相同

但是,我想要的是

{
 ('zebra', 1): Int64Index([0], dtype='int64'),
 ('zebra', 2): Int64Index([1], dtype='int64'),
 ('apple', 3): Int64Index([2], dtype='int64'),
 ('apple', 4): Int64Index([3], dtype='int64')
}
当按一列分组时,

'sort = False'似乎工作正常。

df_agg = df.groupby(by=['ColA'], sort = False)
df_agg.groups

结果

{'zebra': Int64Index([0, 1], dtype='int64'),
 'apple': Int64Index([2, 3], dtype='int64')}

如果排序仅适用于一列而不适用于元组。我可以根据元组对分组字典进行排序,但是我使用的应用程序需要一个分组对象。我很感激如何解决这个问题。

2 个答案:

答案 0 :(得分:3)

我们使用伪排序键,在这里我使用pd.factorize创建一个:

df.assign(sortkey=pd.factorize(df['ColA'])[0]).groupby(['sortkey', 'ColA', 'ColB']).groups

输出:

{(0, 'zebra', 1): Int64Index([0], dtype='int64'),
 (0, 'zebra', 2): Int64Index([1], dtype='int64'),
 (1, 'apple', 3): Int64Index([2], dtype='int64'),
 (1, 'apple', 4): Int64Index([3], dtype='int64')}

答案 1 :(得分:3)

groups属性是一个字典,用于确定组的顺序。您必须通过一些操作来“解析” groupby对象,以确定顺序是/是什么。

df.groupby(['ColA', 'ColB'], sort=False, as_index=False).first()

    ColA  ColB  ColC
0  zebra     1    10
1  zebra     2    10
2  apple     3    20
3  apple     4    20

df.groupby(['ColA', 'ColB'], as_index=False).first()

    ColA  ColB  ColC
0  apple     3    20
1  apple     4    20
2  zebra     1    10
3  zebra     2    10

实际的查找位置是groupby对象的ngroup方法

g1 = df.groupby(['ColA', 'ColB'], sort=False, as_index=False)
g1.ngroup()

0    0
1    1
2    2
3    3
dtype: int64

g2 = df.groupby(['ColA', 'ColB'], as_index=False)
g2.ngroup()

0    2
1    3
2    0
3    1
dtype: int64
相关问题