Pandas特殊方式重索引时间序列并实现条件前向填充
解决方案
要实现「仅在原始数据存在的时间段内对time列做向前填充(ffill),时间缺口处保留NaN」的需求,可以通过标记原始数据区间 + 分组填充的方式完成,具体步骤如下:
1. 预处理原始数据
先将UNIX时间转换为UTC+0的datetime格式,保留time列同时准备好用于重索引的时间基准:
import pandas as pd # 模拟原始数据集(替换为你的实际数据) raw_data = { "unix_time": [1620000000, 1620003600, 1620010800], # 对应UTC 2021-05-03 00:00、01:00、03:00(存在2小时缺口) "value": [10, 20, 30] } df = pd.DataFrame(raw_data) # 转换UNIX时间为UTC datetime,生成time列 df["time"] = pd.to_datetime(df["unix_time"], unit="s", utc=True)
2. 生成5分钟步长的完整时间索引
用pd.date_range生成覆盖原始数据首尾时间的5分钟间隔索引,用于扩展数据集:
# 生成从最早到最晚时间的5分钟步长索引 full_time_index = pd.date_range( start=df["time"].min(), end=df["time"].max(), freq="5min" )
3. 重索引并标记原始数据区间
将数据集重索引到5分钟步长,同时标记出原始数据存在的行:
# 临时将time设为索引,完成重索引后恢复为列 df_temp = df.set_index("time") df_reindexed = df_temp.reindex(full_time_index).reset_index().rename(columns={"index": "timestamp"}) # 标记原始数据存在的行(time列非空即为原始数据行) df_reindexed["is_original"] = df_reindexed["time"].notna()
4. 分组实现定向ffill
核心是通过分组,仅在连续的原始数据区间内做向前填充,缺口区域不填充:
# 生成分组键:每遇到一个时间缺口(is_original为False),分组编号+1 group_key = (~df_reindexed["is_original"]).cumsum() # 对每个分组的time列做ffill,仅当分组内存在原始数据时才填充 df_reindexed["time_filled"] = df_reindexed.groupby(group_key)["time"].transform( lambda x: x.ffill() if x.notna().any() else x )
效果验证
最终的time_filled列即为需求结果:原始数据所在的连续时间段内(如00:0001:00、03:00之后)会向前填充`time`值,而时间缺口(如01:0502:55)则保留NaN。
示例输出片段:
timestamp time time_filled value 0 2021-05-03 00:00:00 2021-05-03 00:00:00 2021-05-03 00:00:00 10.0 1 2021-05-03 00:05:00 NaN 2021-05-03 00:00:00 NaN ... 12 2021-05-03 01:00:00 2021-05-03 01:00:00 2021-05-03 01:00:00 20.0 13 2021-05-03 01:05:00 NaN NaN NaN ... 35 2021-05-03 02:55:00 NaN NaN NaN 36 2021-05-03 03:00:00 2021-05-03 03:00:00 2021-05-03 03:00:00 30.0 37 2021-05-03 03:05:00 NaN 2021-05-03 03:00:00 NaN
内容的提问来源于stack exchange,提问作者Vladyslav Archivadze
相关产品推荐
相关产品推荐

