【问题标题】:Pandas groupby drops group columns after fillna in 1.1.0Pandas groupby 在 1.1.0 中的 fillna 之后删除了组列
【发布时间】:2020-11-26 01:22:15
【问题描述】:

我有一段曾经在 1.0.5 版中工作的 pandas 代码。这是我的问题的一个简化的、独立的示例:

import pandas as pd

df = pd.DataFrame(data=[
    ('bk1', 10),
    ('bk1', None),
    ('bk1', 13),
    ('bk1', None),
    ('bk2', None),
    ('bk2', 14),
    ('bk3', 12),
    ('bk3', None),
], columns=('book', 'price'))


grouped = df.groupby(['book'], as_index=False, sort=False)
df = grouped.fillna(method='ffill')

print(df)

在此示例中,我们有一个图书销售列表,其中缺少一些价格。我们正在尝试使用前一行来填充缺失的数据,其中该行是同一本书。

在 Pandas 1.0.5 中,这会生成一个包含两列的数据框:

  book  price
0  bk1   10.0
1  bk1   10.0
2  bk1   13.0
3  bk1   13.0
4  bk2    NaN
5  bk2   14.0
6  bk3   12.0
7  bk3   12.0

在 Pandas 1.1.0 中,这会删除 book 列,这会使输出无法使用。

   price
0   10.0
1   10.0
2   13.0
3   13.0
4    NaN
5   14.0
6   12.0
7   12.0

我已经阅读了patch notes for version 1.1.0,但我找不到任何关于此更改的评论。

问题:

  1. 这是 Pandas 中的错误,还是我依赖​​于未定义的行为?
  2. 有没有更自然的表达方式?

您可能会问的问题:

  1. 为什么不使用没有 groupby 的 fillna?

    在本例中,bk2 的第一行没有价格,但用上一行填充它没有任何意义,即 bk1 的价格。

  2. 为什么使用 ffill 而不是删除 NA 值?

    我的真实代码正在处理时间序列数据,而 ffill 是表达最后一个已知观察结果的最自然方式。

【问题讨论】:

  • 不是bug ....ffill是前一个not nan , bk2, NaN 显示在第1位的填充NaN,所以不会被填充
  • 这是故意的。我不希望 ffill 在组之间填充。请参阅“您可能会问的问题 #1”。问题是缺少列。

标签: python pandas pandas-groupby


【解决方案1】:

解决方法

groupby可以表示为:

df = grouped.apply(lambda df: df.fillna(method='ffill'))

这在两个版本中都适用。

原因

此问题可能与此更改有关,尽管它发生在不同的版本中:

DataFrameGroupBy 的方法ffillbfillpadbackfill 之前在返回值中包含了组标签,这与其他groupby 转换不一致。现在只返回填充的值。 (GH21521)

(Source.)

【讨论】:

  • a transform 也可以在这里工作,有一个任务。我冒险它会比在这种情况下应用更快。不过,原因很好。 df["price"] = grouped.transform("ffill")
【解决方案2】:

您可以通过使用 update 函数采取不同的方法来解决此问题(不同于 Nick ODell 提出的解决方案):

df.update(df.groupby(['book']).ffill())
print(df)
Out[1]: 
  book  price
0  bk1   10.0
1  bk1   10.0
2  bk1   13.0
3  bk1   13.0
4  bk2    NaN
5  bk2   14.0
6  bk3   12.0
7  bk3   12.0

这也适用于两个版本。

【讨论】:

    猜你喜欢
    • 2013-05-30
    • 1970-01-01
    • 2021-04-15
    • 2016-10-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-08-02
    相关资源
    最近更新 更多