You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Python中按1年时间偏移DataFrame列值?

用Pandas按时间偏移获取去年同期值

你需要的是根据日期匹配去年同期的value值,而非单纯偏移索引或行数。之前用shift(12, freq='MS')的方式只会偏移索引的时间,不会自动匹配原数据中对应去年日期的数值,尤其当你的时间序列不连续时(比如示例里缺了2020年2-7月的记录),这种方法完全不适用。

方法一:生成去年日期后合并匹配

先给每条记录生成去年同期的日期,再通过合并操作匹配对应的值:

import pandas as pd
import numpy as np

test_df = pd.DataFrame({'dt':['2020-01-01', '2020-08-01', '2021-01-01', '2022-01-01'],
                        'value':[10,13,15,14]})

test_df['dt'] = pd.to_datetime(test_df['dt'])
# 生成去年同期日期
test_df['dt_py'] = test_df['dt'] - pd.DateOffset(years=1)
# 合并原数据,匹配去年日期对应的value
test_df = test_df.merge(test_df[['dt', 'value']], left_on='dt_py', right_on='dt', how='left', suffixes=('', '_py'))
# 清理多余列
test_df = test_df.drop(columns=['dt_py', 'dt_y'])
print(test_df)

输出结果:

dt  value  value_py
0 2020-01-01     10       NaN
1 2020-08-01     13       NaN
2 2021-01-01     15      10.0
3 2022-01-01     14      15.0

方法二:用字典映射快速取值

先构建日期到value的映射字典,再通过日期偏移后直接取值,代码更简洁:

import pandas as pd
import numpy as np

test_df = pd.DataFrame({'dt':['2020-01-01', '2020-08-01', '2021-01-01', '2022-01-01'],
                        'value':[10,13,15,14]})

test_df['dt'] = pd.to_datetime(test_df['dt'])
# 创建日期到value的映射
dt_value_map = test_df.set_index('dt')['value'].to_dict()
# 对每个日期偏移一年后取对应值,无匹配则返回NaN
test_df['value_py'] = test_df['dt'].apply(lambda x: dt_value_map.get(x - pd.DateOffset(years=1), np.nan))
print(test_df)

输出和方法一完全一致。

为什么之前的shift方法无效?

当shift函数传入freq参数时,它的作用是偏移时间序列的索引——也就是把每条记录的索引时间往后/往前移动指定频率,但不会去检查原数据中是否存在这个偏移后的日期,更不会自动匹配对应数值。你的数据不是连续的月度序列,所以这种方法无法得到你想要的value_py结果。

内容的提问来源于stack exchange,提问作者mf17

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.06 02:21:02