Pandas:周转日重采样并ffill填充结果异常的问题排查
周转日重采样+前向填充(含前置日期)问题分析
你遇到的问题是因为**loffset参数误用**导致重采样范围被截断,同时默认的重采样不会自动包含第一个数据点之前的日期,咱们一步步解决:
问题回顾
你的原始数据是两个周日的记录:
Date Val 0 2018-01-07 1 1 2018-01-14 2
你期望得到从2018-01-01(第一个周日往前6天)到2018-01-14的完整日数据,每个日期用最近的周日值填充,但现有代码只输出到2018-01-08就停止了。
错误原因拆解
loffset的误用:你设置的loffset=pd.offsets.DateOffset(-6)是把重采样后的所有索引整体往前偏移6天,这会把原始最后一个数据点2018-01-14偏移到2018-01-08,导致重采样的时间范围直接截止到这个偏移后的日期,后续2018-01-09至2018-01-14的日期根本没被纳入处理范围。- 默认重采样不包含前置日期:即使去掉
loffset,默认的resample('D')只会从第一个数据点(2018-01-07)开始生成日期,不会自动包含之前的2018-01-01至2018-01-06。
修正后的解决方案
要实现你的需求,需要先构建完整的日期范围,再用前向填充补齐缺失值,这里有两种靠谱的方式:
方式一:用reindex构建完整日期范围(最直观)
import pandas as pd # 原始数据 df = pd.DataFrame({'Date': ['2018-01-07', '2018-01-14'], 'Val': [1, 2]}) # 转换日期格式并设为索引 df['Date'] = pd.to_datetime(df['Date']) df.set_index('Date', inplace=True) # 生成你需要的完整日期范围:从2018-01-01到2018-01-14 full_date_range = pd.date_range(start='2018-01-01', end='2018-01-14', freq='D') # 重新索引到完整日期,并用前向填充补齐缺失值 df_result = df.reindex(full_date_range).ffill() # 把索引还原为列(和你期望的格式一致) df_result = df_result.reset_index().rename(columns={'index': 'Date'}) print(df_result)
方式二:用resample指定起始点(更适合动态场景)
如果你不想手动写死起始日期,可以用resample的origin参数,结合ffill实现:
import pandas as pd df = pd.DataFrame({'Date': ['2018-01-07', '2018-01-14'], 'Val': [1, 2]}) df['Date'] = pd.to_datetime(df['Date']) df.set_index('Date', inplace=True) # 以2018-01-01为采样起始点,重采样为日频率后填充 df_result = df.resample('D', origin='2018-01-01').ffill().reset_index() print(df_result)
两种方式都会输出你期望的结果:
Date Val 0 2018-01-01 1 1 2018-01-02 1 2 2018-01-03 1 3 2018-01-04 1 4 2018-01-05 1 5 2018-01-06 1 6 2018-01-07 1 7 2018-01-08 2 8 2018-01-09 2 9 2018-01-10 2 10 2018-01-11 2 11 2018-01-12 2 12 2018-01-13 2 13 2018-01-14 2
额外提示
loffset一般用于调整采样结果的索引对齐(比如把月末数据偏移到月初),不适合用来扩展采样范围。- 如果你的数据是固定每周日的记录,也可以用
pd.date_range生成每周日的序列,再扩展到日频率,逻辑是一样的。
内容的提问来源于stack exchange,提问作者ResidentSleeper
相关产品推荐
相关产品推荐

