Избегайте цикла с символьной переменной - PullRequest
1 голос
/ 09 мая 2019

Я бы хотел использовать lapply вместо цикла for. Он собирается суммировать несколько переменных для создания новых, таких как .. @ 3, ... @ 6 и т. Д.

Я пытался использовать noquote, чтобы избавиться от "", но я всегда получаю следующее сообщение об ошибке:

Error in roll_mean_impl(x, as.integer(n), as.numeric(weights), as.integer(by),  : 
  Not compatible with requested type: [type=character; target=double].
In addition: Warning message:
In `[.data.table`(setDT(input.agg), , `:=`(paste0(Var.List[j], sep = ".",  :
  NAs introduced by coercion

Var.List <- c("Price.min", "Price.max")
k.List <- c(3, 6, 12)
for (j in 1:length(Var.List)){
  lapply(k.List, function(i)
    setDT(input.agg)[, paste0(Var.List[j], sep=".", i) := if(.N > 1) c(cumsum(noquote(Var.List[j])[1:(i-1)])/1:(i-1), 
      roll_mean(noquote(Var.List[j]), n=i, align='right')) else as.numeric(noquote(Var.List[j])), BO_ID])
}

С помощью следующего кода я получил ожидаемые результаты:

k.List <- c(3, 6, 12)
lapply(k.List, function(i)
    setDT(input.agg)[, paste0("Price.min", sep=".", i) := if(.N > 1) c(cumsum(Price.min[1:(i-1)])/1:(i-1), 
      roll_mean(Price.min, n=i, align='right')) else as.numeric(Price.min), BO_ID])
lapply(k.List, function(i)
  setDT(input.agg)[, paste0("Price.max", sep=".", i) := if(.N > 1) c(cumsum(Price.max[1:(i-1)])/1:(i-1), 
    roll_mean(Price.max, n=i, align='right')) else as.numeric(Price.max), BO_ID])

input.agg выглядит так:

                BO_ID Timestamp_Date_YM Price.min Price.max
1: XXXXXXXXXXXXXXXXXX1        201801        30       152
2: XXXXXXXXXXXXXXXXXX1        201802        13       166
3: XXXXXXXXXXXXXXXXXX1        201803        39       155
4: XXXXXXXXXXXXXXXXXX1        201804        14       198
5: XXXXXXXXXXXXXXXXXX1        201805        79       194
6: XXXXXXXXXXXXXXXXXX1        201806        23       190
...