TryCatch namespace?

I am completely new to R and am confused by the correct use of tryCatch . My goal is to make a forecast for a large data set. If predictions cannot fit into memory, I want to work around the problem by dividing my data.

My code now looks something like this:

 tryCatch({ large_vector = predict(model, large_data_frame) }, error = function(e) { # I ran out of memory for (i in seq(from = 1, to = dim(large_data_frame)[1], by = 1000)) { small_vector = predict(model, large_data_frame[i:(i+step-1), ]) save(small_vector, tmpfile) } rm(large_data_frame) # free memory large_vector = NULL for (i in seq(from = 1, to = dim(large_data_frame)[1], by = 1000)) { load(tmpfile) unlink(tmpfile) large_vector = c(large_vector, small_vector) } }) 

The fact is that if an error does not occur, the large_vector populated with my predictions, as expected. If an error occurs, large_vector seems to exist only in the error code namespace, which makes sense because I declared it as a function. For the same reason, I get a warning that large_data_frame cannot be deleted.

Unfortunately, this is not what I want. I would like to assign a large_vector variable from my error function. I decided that one of the possibilities was to specify the environment and use the assignment. Thus, I would use the following instructions in my error code:

 rm(large_data_frame, envir = parent.env(environment())) [...] assign('large_vector', large_vector, parent.env(environment())) 

However, this decision seems rather dirty to me. I wonder if there is an opportunity to achieve my goal with the help of "clean" code?

[EDIT] There seems to be some confusion because I put the code above to illustrate the problem, rather than give a working example. Here is a minimal example that shows a problem with namespace:

 # Example 1 : large_vector fits into memory rm(large_vector) tryCatch({ large_vector = rep(5, 1000) }, error = function(e) { # do stuff to build the vector large_vector = rep(3, 1000) }) print(large_vector) # all 5 # Example 2 : pretend large_vector does not fit into memory; solution using parent environment rm(large_vector) tryCatch({ stop(); # simulate error }, error = function(e) { # do stuff to build the vector large_vector = rep(3, 1000) assign('large_vector', large_vector, parent.env(environment())) }) print(large_vector) # all 3 # Example 3 : pretend large_vector does not fit into memory; namespace issue rm(large_vector) tryCatch({ stop(); # simulate error }, error = function(e) { # do stuff to build the vector large_vector = rep(3, 1000) }) print(large_vector) # does not exist 
+4
source share
3 answers

I would do something like this:

 res <- tryCatch({ large_vector = predict(model, large_data_frame) }, error = function(e) { # I ran out of memory ll <- lapply(split(data,seq(1,nrow(large_data_frame),1000)), function(x) small_vector = predict(model, x)) return(ll) }) rm(large_data_frame) if(is.list(ll)) res <- do.call(rbind,res) 

The idea is to return a list of forecast results if you run out of memory.

NOTE. I am not sure about this because we do not have a reproducible example.

+5
source

EDIT: try again:

You can use finally tryCatch argument:

 step<-1000 n<-dim(large_data_frame)[1] large_vector <- NULL tryCatch({ large_vector <- predict(model, large_data_frame) }, error = function(e) { # ran out of memory for (i in seq(from = 1, to = n, by = step)) { small_vector <- predict(model, large_data_frame[i:(i+step-1),]) #predict in pieces save(small_vector,file=paste0("tmpfile",i)) #same pieces } rm(large_data_frame) #free memory },finally={if(is.null(large_vector)){ #if we run out of memory large_vector<-numeric(n) #make vector for (i in seq(from = 1, to = n, by = step)){ #collect pieces load(paste0("tmpfile",i)) large_vector[i:(i+step-1)] <- small_vector } }}) 

Here is a simplified version to see what happens:

 large_vector<-NULL rm(y) tryCatch({ large_vector <- y }, error = function(e) {# y is not found print("error") },finally={if(is.null(large_vector)){ large_vector<-1 }}) > large_vector [1] 1 

EDIT2: Another tip regarding an area that might be useful to you (although maybe not in this situation, since you did not want to declare large_vector in advance): The <<- operator <<- from R-help:

The <<and →> operators are usually used only in functions and invoke a search performed through the parent environment for the existing definition of an assigned variable ...

Therefore, you can use the above code example as follows:

 large_vector<-NULL rm(y) tryCatch({ large_vector <- y }, error = function(e) {# y is not found large_vector <<- 1 print("error") }) > large_vector [1] 1 
+3
source

The code below is quite explanatory. In fact, the problem is that everything that is inside the error function does not apply to the parent environment by default.

b = 0

as explained, this does not work:

tryCatch (expr = {stop ("error1")}, error = function (e) {b = 1})
b

SOLUTION 1: assign a parent environment

tryCatch (expr = {stop ("error2")}, error = function (e) {assign (x = "b", value = 2, envir = parent.env (env = environment ())))
b

SOLUTION 2: the simplest (only works if you assign b to both expr and error )

b = tryCatch (expr = {stop ("error3")}, error = function (e) {b = 3; return (b)})
b

0
source

All Articles