用季度值插入 R 年度时间序列数据

interpolating in R yearly time series data with quarterly values

我有一个数据集,其中包含 ID、年份和收入列表。我正在尝试将年度值插入季度值。

id = c(2, 2, 2, 3, 3, 3,4,4,4,5,5)
year = c(2000, 2001, 2002, 2000,2001,2002, 2000,2001,2002,2000,2002)
income = c(20, 24, 26, 30,34,36, 40,46,48,53,56)
df = data.frame(id, year, income)

例如,我希望获得 2000Q1、2000Q2、2000Q3、2000Q4、2001Q1、...、2001Q4 年度季度的(插值)收入值。所以数据框将是 id,year-quarter,income。收入将基于内插收入。

我意识到线性插值时,趋势只能基于各自的ID。关于如何在 R 中进行插值有什么建议吗?

我喜欢使用此约定将数据帧拆分为子集(在您的情况下为 'id' 的唯一值),对每个子集应用一个函数,然后将数据帧放回原处。

df2 <- do.call("rbind", lapply(split(df, df$id), function(df_subset) {

  # the operations inside these brackets will be appied to a subset dataframe
  #   that is equivalent to doing 'subset(df, id == x)' where x is each unique value of id

  return(df_subset) # this just returns df_subset unchanged, but you alter it in any way you need

}))

有几种方法可以进行线性插值,但我个人默认使用 'zoo' 包中的 na.approx() 。您需要将代表每个季度的行添加到您的数据框中,其 income 值为 NA。然后 na.approx 将用内插值填充它们,如 df_subset$income_interpolated <- na.approx(df_subset$income)

这是一个使用 dplyr 的例子:

library(dplyr)

annual_data <- data.frame(
    person=c(1, 1, 1, 2, 2),
    year=c(2010, 2011, 2012, 2010, 2012),
    y=c(1, 2, 3, 1, 3)
    )

expand_data <- function(x) {
    years <- min(x$year):max(x$year)
    quarters <- 1:4
    grid <- expand.grid(quarter=quarters, year=years)
    x$quarter <- 1
    merged <- grid %>% left_join(x, by=c('year', 'quarter'))
    merged$person <- x$person[1]
    return(merged)
}

interpolate_data <- function(data) {
    xout <- 1:nrow(data)
    y <- data$y
    interpolation <- approx(x=xout[!is.na(y)], y=y[!is.na(y)], xout=xout)
    data$yhat <- interpolation$y
    return(data)
}

expand_and_interpolate <- function(x) interpolate_data(expand_data(x))

quarterly_data <- annual_data %>% group_by(person) %>% do(expand_and_interpolate(.))

print(as.data.frame(quarterly_data))

这种方法的输出是:

   quarter year person  y yhat
1        1 2010      1  1 1.00
2        2 2010      1 NA 1.25
3        3 2010      1 NA 1.50
4        4 2010      1 NA 1.75
5        1 2011      1  2 2.00
6        2 2011      1 NA 2.25
7        3 2011      1 NA 2.50
8        4 2011      1 NA 2.75
9        1 2012      1  3 3.00
10       2 2012      1 NA   NA
11       3 2012      1 NA   NA
12       4 2012      1 NA   NA
13       1 2010      2  1 1.00
14       2 2010      2 NA 1.25
15       3 2010      2 NA 1.50
16       4 2010      2 NA 1.75
17       1 2011      2 NA 2.00
18       2 2011      2 NA 2.25
19       3 2011      2 NA 2.50
20       4 2011      2 NA 2.75
21       1 2012      2  3 3.00
22       2 2012      2 NA   NA
23       3 2012      2 NA   NA
24       4 2012      2 NA   NA

可能有很多方法可以清理它。使用的关键函数是 expand.gridapproxdplyr::group_byapprox 函数有点棘手。查看 zoo::na.approx.default 的实现对于弄清楚如何使用 approx 非常有帮助。