繁体   English   中英

大熊猫:填写重复日期时填写缺失的日期

[英]pandas: Fill missing dates when keeping duplicates

我有一个简单的pandas系列:

import pandas as pd

quantities = [1, 14, 14, 11, 12, 13, 14]
timestamps = [pd.Timestamp(2015, 4, 1), pd.Timestamp(2015, 4, 1), pd.Timestamp(2015, 4, 2), pd.Timestamp(2015, 4, 3), pd.Timestamp(2015, 4, 4), pd.Timestamp(2015, 4, 5), pd.Timestamp(2015, 4, 8)]
series = pd.Series(quantities, index=timestamps)

如下所示:

2015-04-01     1
2015-04-01    14
2015-04-02    14
2015-04-03    11
2015-04-04    12
2015-04-05    13
2015-04-08    14
dtype: int64

我想填写缺失的日期,即2015-04-06 = NaN2015-04-07 = NaN但保持序列不变,即:

2015-04-01     1
2015-04-01    14
2015-04-02    14
2015-04-03    11
2015-04-04    12
2015-04-05    13
2015-04-06    NaN
2015-04-07    NaN
2015-04-08    14
dtype: int64

我试过了:

series = series.asfreq('D')

但出现以下错误: ValueError:无法从重复的轴重新索引 由于重复的时间戳值而发生此错误。

地球上有什么办法可以做到这一点?

谢谢你的帮助。

我们试试吧:

s = pd.Series(np.nan, index=pd.date_range(series.index.min(), series.index.max(), freq='D'))
pd.concat([series,s[~s.index.isin(series.index)]]).sort_index()

输出:

2015-04-01     1.0
2015-04-01    14.0
2015-04-02    14.0
2015-04-03    11.0
2015-04-04    12.0
2015-04-05    13.0
2015-04-06     NaN
2015-04-07     NaN
2015-04-08    14.0
dtype: float64

时序:

%%timeit
temp = series[~series.index.duplicated(keep='first')].asfreq('D')
pd.concat([series, temp.loc[~temp.index.isin(series.index)]]).sort_index()

每个循环2.51 ms±52.7 µs(平均±标准偏差,共运行7次,每个循环100个)

%%timeit
series.name = "x"
calendar = pd.DataFrame(None, index=pd.DatetimeIndex(start=series.index.min(), end=series.index.max(), freq='D'))
calendar.join(series)

C:\\ ProgramData \\ Anaconda3 \\ lib \\ site-packages \\ ipykernel_launcher.py:2:FutureWarning:不建议通过传递范围端点来创建DatetimeIndex。 请改用pandas.date_range

每个循环2.07 ms±27.1 µs(平均±标准偏差,共运行7次,每个循环100个)

%%timeit
s = pd.Series(np.nan, index=pd.date_range(series.index.min(), series.index.max(), freq='D'))
pd.concat([series,s[~s.index.isin(series.index)]]).sort_index()

每个循环1.86 ms±15.4 µs(平均±标准偏差,共运行7次,每个循环1000个)

感谢@root的建议。

%%timeit
s = pd.Series(index=pd.date_range(series.index.min(), series.index.max(), freq='D')\
                      .difference(series.index))
pd.concat([series,s]).sort_index()

每个循环1.55 ms±11.6 µs(平均±标准偏差,共运行7次,每个循环1000次)

假设您没有数百万行,这应该足够了:

series.name = "x"
calendar = pd.DataFrame(None, index=pd.DatetimeIndex(start=series.index.min(), end=series.index.max(), freq='D'))
calendar.join(series)

输出:

               x
2015-04-01   1.0
2015-04-01  14.0
2015-04-02  14.0
2015-04-03  11.0
2015-04-04  12.0
2015-04-05  13.0
2015-04-06   NaN
2015-04-07   NaN
2015-04-08  14.0

如果需要序列,则可以访问结果DataFrame的列x: calendar.join(series).x

您可以使用pandas.concat 添加到您的示例代码:

series2 = pd.Series([pd.np.nan, pd.np.nan],
                    index=[pd.Timestamp(2015, 4, 6), 
                           pd.Timestamp(2015, 4, 7)])

pd.concat([series, series2], axis=0).sort_index()

回报

2015-04-01     1.0
2015-04-01    14.0
2015-04-02    14.0
2015-04-03    11.0
2015-04-04    12.0
2015-04-05    13.0
2015-04-06     NaN
2015-04-07     NaN
2015-04-08    14.0
dtype: float64

也就是说,使用非唯一索引会使您面临更多的困难。 您将受益于具有唯一的索引级别或非索引字段以用于消除歧义。

您可以使用asfreq删除索引重复项,然后在temp.index 不在原始Serie中的情况下进行concat

temp = series[~series.index.duplicated(keep='first')].asfreq('D')
pd.concat([series, temp.loc[~temp.index.isin(series.index)]]).sort_index()

output:
2015-04-01     1.0
2015-04-01    14.0
2015-04-02    14.0
2015-04-03    11.0
2015-04-04    12.0
2015-04-05    13.0
2015-04-06     NaN
2015-04-07     NaN
2015-04-08    14.0
dtype: float64

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM