如何基于tsibble实现自定义三个月周期的时间序列聚合?
自定义跨年度季度区间聚合tsibble数据
问题描述
现有月度tsibble数据,需要按非标准季度区间聚合,分组规则如下:
- Dec-Jan-Feb(跨年度,如Dec2023-Jan2024-Feb2024为一组)
- Mar-Apr-May
- Jun-Jul-Aug
- Sept-Oct-Nov
需使用tsibble的index_by函数实现自定义分组聚合。
解决方案
核心思路是为每个月份生成对应自定义区间的时间标识,确保跨年度的月份被分到同一组,同时保持tsibble索引的有序性。我们用区间的结束月份作为该组的索引(如Dec-Jan-Feb区间用Feb的yearmonth标识),既符合时间顺序,又能让tsibble识别为有效索引。
步骤1:编写自定义区间转换函数
创建函数将yearmonth类型的日期转换为对应区间的结束月份:
library(tsibble) library(dplyr) library(lubridate) custom_quarter_end <- function(x) { m <- month(x) case_when( # 12月归属到下一年的2月作为区间结束 m == 12 ~ x + months(2), # 1-2月归属到当年2月 m %in% 1:2 ~ yearmonth(paste(year(x), 2, sep = "-")), # 3-5月归属到当年5月 m %in% 3:5 ~ yearmonth(paste(year(x), 5, sep = "-")), # 6-8月归属到当年8月 m %in% 6:8 ~ yearmonth(paste(year(x), 8, sep = "-")), # 9-11月归属到当年11月 m %in% 9:11 ~ yearmonth(paste(year(x), 11, sep = "-")) ) }
步骤2:使用index_by进行聚合
结合自定义函数,按key分组后聚合数值:
data.custom <- data |> index_by(custom_quarter = ~custom_quarter_end(.)) |> group_by_key() |> summarise(total_value = sum(value))
验证结果
查看聚合后的数据,Dec2023、Jan2024、Feb2024会被合并到2024-02对应的组中:
# 查看AT地区2024年2月对应的聚合值 filter(data.custom, geo == "AT", custom_quarter == yearmonth("2024-02"))
可选:添加自定义区间标签
如果需要更直观的区间名称,可以额外生成标签列:
data.custom_labeled <- data.custom |> mutate( quarter_label = case_when( month(custom_quarter) == 2 ~ paste0(year(custom_quarter), "-Dec-Jan-Feb"), month(custom_quarter) == 5 ~ paste0(year(custom_quarter), "-Mar-Apr-May"), month(custom_quarter) == 8 ~ paste0(year(custom_quarter), "-Jun-Jul-Aug"), month(custom_quarter) == 11 ~ paste0(year(custom_quarter), "-Sept-Oct-Nov") ) )
内容的提问来源于stack exchange,提问作者umbe1987
相关产品推荐
相关产品推荐

