如何用tidy的accumulate函数基于前一期值计算tibble的value列?
使用tidyverse的accumulate函数计算递推value值
问题说明
现有如下tibble数据:
df <- tibble(return = c(NA, 0.120436251, -0.019871515, 0.024876142, -0.013786987, -0.012571415), value = c(100, NA, NA, NA, NA, NA))
需要通过公式(1+return)*lag(value)计算首行以外所有行的value值,预期输出:
df_1 <- tibble(return = c(NA, 0.120436251, -0.019871515, 0.024876142, -0.013786987, -0.012571415), value = c(100, 112.0436, 109.8171, 112.5490, 110.9973, 109.6019))
Base R中可通过for循环实现:
df_1 = df for (i in 2:nrow(df_1)){ df_1$value[i] <- df_1$value[i-1]*(1+df_1$return[i]) }
尝试用tidy风格的accumulate函数时,代码返回列表而非正确数值:
df <- df %>% mutate(Value = accumulate(value, ~if(is.na(.y)) .x*(1+df$return) else .y))
正确解决方案
原代码错误在于使用了整个df$return向量而非对应迭代步骤的单个值,且accumulate默认仅处理单序列。这里需要同时迭代前一步的value和当前行的return,使用accumulate2更合适:
library(tidyverse) df <- tibble(return = c(NA, 0.120436251, -0.019871515, 0.024876142, -0.013786987, -0.012571415), value = c(100, NA, NA, NA, NA, NA)) df_1 <- df %>% mutate(value = { # 用accumulate2处理return序列(从第2个元素开始)和初始value iter_results <- accumulate2( .x = return[-1], .y = value[1], .f = function(prev_val, curr_return) prev_val * (1 + curr_return) ) # 合并初始值和迭代结果,转为向量 c(value[1], unlist(iter_results)) }) print(df_1)
代码说明
accumulate2(.x = return[-1], .y = value[1]):.x传入从第2行开始的return值,.y传入初始的value值(100).f定义递推逻辑:用前一步的value乘以(1+当前return)- 最后将初始值和迭代结果合并,替换原value列
内容的提问来源于stack exchange,提问作者MF1992
相关产品推荐
相关产品推荐

