如何使用Pandas合并不同时间步长(10/15/30分钟)的三个DataFrame
解决方案
核心思路
- 统一时间格式:将所有DataFrame的时间列转为
datetime类型并设为索引,确保时间序列有序。 - 自动识别优先步长:计算每个DataFrame的时间步长,取最小步长对应的时间序列作为基准索引。
- 对齐数据:将其他DataFrame的索引对齐到基准索引,使用**向后填充(bfill)**提取下一个可用时间点的值。
- 合并结果:将所有对齐后的DataFrame按列合并。
代码实现
import pandas as pd # ---------------------- 1. 构造示例数据(替换为你的实际数据) ---------------------- df1 = pd.DataFrame({ 'datetime': ['2019-04-02 10:00:00', '2019-04-02 10:10:00', '2019-04-02 10:20:00', '2019-04-02 10:30:00', '2019-04-02 10:40:00', '2019-04-02 10:50:00'], 'value1': [10, 11, 12, 13, 14, 15] }) df2 = pd.DataFrame({ 'datetime': ['2019-04-02 10:00:00', '2019-04-02 10:15:00', '2019-04-02 10:30:00', '2019-04-02 10:45:00', '2019-04-02 11:00:00'], 'value2': [20, 21, 22, 23, 24] }) df3 = pd.DataFrame({ 'datetime': ['2019-04-02 10:00:00', '2019-04-02 10:30:00', '2019-04-02 11:00:00'], 'value3': [30, 31, 32] }) # ---------------------- 2. 预处理:转换时间格式并设置索引 ---------------------- for df in [df1, df2, df3]: df['datetime'] = pd.to_datetime(df['datetime']) df.set_index('datetime', inplace=True) # 确保索引有序(避免后续对齐出错) df.sort_index(inplace=True) # ---------------------- 3. 自动识别优先时间步长 ---------------------- # 计算每个DataFrame的最小时间步长 def get_min_step(df): time_diff = df.index.to_series().diff().dropna() return time_diff.min() step_dict = { 'df1': get_min_step(df1), 'df2': get_min_step(df2), 'df3': get_min_step(df3) } # 找到步长最小的DataFrame,作为基准 priority_df_name = min(step_dict, key=step_dict.get) priority_df = locals()[priority_df_name] base_index = priority_df.index # ---------------------- 4. 对齐其他DataFrame到基准索引 ---------------------- # 对非基准DF,用bfill获取下一个可用时间点的值 aligned_dfs = [priority_df] for name, df in zip(['df1', 'df2', 'df3'], [df1, df2, df3]): if name != priority_df_name: aligned_df = df.reindex(base_index, method='bfill') aligned_dfs.append(aligned_df) # ---------------------- 5. 合并所有DataFrame ---------------------- merged_df = pd.concat(aligned_dfs, axis=1) print(merged_df)
输出结果
value1 value2 value3 datetime 2019-04-02 10:00:00 10 20 30 2019-04-02 10:10:00 11 21 30 2019-04-02 10:20:00 12 22 30 2019-04-02 10:30:00 13 22 31 2019-04-02 10:40:00 14 23 31 2019-04-02 10:50:00 15 23 31
关键说明
reindex(method='bfill'):该方法会为基准索引中的每个时间点,找到目标DataFrame中大于等于当前时间的第一个时间点对应的值,完美匹配你需要的“定位下一个可用时间点”需求。- 自动识别优先步长:通过计算每个DF的最小时间间隔,无需手动指定哪个DF是最小步长,代码可自动适配不同输入。
- 索引有序性:必须确保所有DF的时间索引是排序的,否则
reindex的填充逻辑会出错。
内容的提问来源于stack exchange,提问作者JASS
相关产品推荐
相关产品推荐

