Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Avoid "optimization failure" in for loop in R

I'm trying to make a lot of time series forecast using the HoltWinters function in R. For this purpose, I use a for loop and inside I call to the function, and save the prediction in a data.frame.

The problem is that some results of the HoltWinters function gives errors, specifically optimization errors:

Error en HoltWinters(TS[[i]]) : optimization failure

This error break the loop.

So what I need is something like "try": if it can make the HoltWinters function, it saves the prediction, otherwise it save the error.

The code below replicates the problem:

data <- list()
data[[1]] <- rnorm(36)
data[[2]] <-
  c(
    24,24,28,24,28,22,18,20,19,22,28,28,28,26,24,
    20,24,20,18,17,21,21,21,28,26,32,26,22,20,20,
    20,22,24,24,20,26
  )
data[[3]] <- rnorm(36)

TS <- list()
Outputs <- list()

for (i in 1:3) {
  TS[[i]] <- ts(data[[i]], start = 1, frequency = 12)
  Function <- HoltWinters(TS[[i]])
  TSpredict <- predict(Function, n.ahead = 1)[1]
  Outputs[[i]] <-
    data.frame(LastReal = TS[[i]][length(TS[[i]])], Forecast = TSpredict)
}

Where i <- 2 The problem is generated.

What I need is that in this example the "Outputs" list is as follows:

> Outputs
[[1]]
   LastReal  Forecast
1 0.5657129 -2.274507

[[2]]
  LastReal Forecast
1    error    error

[[3]]
   LastReal   Forecast
1 0.4039783 -0.9556881

Thanks in advance.

like image 300
faaabyan Avatar asked Nov 10 '22 13:11

faaabyan


1 Answers

I ran into this same problem with HoltWinters the other day and took Roman's advice by using tryCatch. It's not the most intuitive to implement based on the documentation, but I found this link very helpful for understanding it: How to write trycatch in R

My solution built off of the sample there.

    data <- list()

data[[1]] <- rnorm(36)
data[[2]] <- c(
  24,24,28,24,28,22,18,20,19,22,28,28,
  28,26,24,20,24,20,18,17,21,21,21,28,
  26,32,26,22,20,20,20,22,24,24,20,26
)
data[[3]] <- rnorm(36)

TS <- list()
Outputs <- list()
result <- list()

for (i in 1:3) {
  Outputs[[i]] <- tryCatch({
    #You can enter messages to see where the loop is
    #message(paste("Computing", i))
    TS[[i]] <- ts(data[[i]], start = 1, frequency = 12)
    Function <- HoltWinters(TS[[i]])
    TSpredict <- predict(Function, n.ahead = 1)[1]
    result[[i]] <-
      data.frame(LastReal = TS[[i]][length(TS[[i]])], Forecast = TSpredict)
  },
  error = function(cond) {
    #message(paste("ERROR: Cannot process for time series:", i))
    msg <- data.frame(LastReal = "error", Forecast = "error")
    return(msg)
  })
}

And for the Outputs

> Outputs
[[1]]
   LastReal  Forecast
1 0.4733632 0.5469373

[[2]]
  LastReal Forecast
1    error    error

[[3]]
   LastReal   Forecast
1 0.8984626 -0.5168826

You can use other error handling parameters such as finally and warning to deal with other exceptions that may arise.

like image 59
hubbs5 Avatar answered Nov 15 '22 07:11

hubbs5