Although a long time user of R, I have little experience to write complex programs in R. During one of my first tries, I experience a unexpected behavior of my code. Namely, if I try to run a function which I have defined my self, a wrapper around a gamlss regression model adaptation, the function fails. running the code within the function line by line interactively works just fine. Weirdly enough, once I have run the code interactively once, the function shows the expected behavior.
Here a minimal reproducible example:
First I load the required packages
library(data.table)
library(gamlss)
I define my wrapper function
fun.wrapper <- function(dt, cores){
all_vars <- colnames(dt)[colnames(dt) > "b"]
scope_vars <- all_vars[1:ceiling(length(all_vars)/2)]
formula_full <- as.formula(paste0("a ~ ", paste(all_vars, collapse = " + ")))
mod0 <- gamlss(formula = formula_full, data = dt, family = "NO", trace = FALSE)
droper <- drop1All(object = mod0, scope = scope_vars, print = FALSE, parallel = ifelse(cores>1, "multicore", "no"), ncpus = cores)
return(droper)
}
I initialize a random data set
data <- data.table(
x = rbinom(size = 1, prob = 0.3, n = 10),
y = rbinom(size = 1, prob = 0.1, n = 10),
z = rbinom(size = 1, prob = 0.2, n = 10),
a = rnorm(n = 10)^2)
and I apply the function to the data, which fails with an error
res_f1 <- fun.wrapper(dt = data, cores = 1)
if I run the code from the wrapper line by line, the results is as expected
dt <- data
cores <- 1
all_vars <- colnames(dt)[colnames(dt) > "b"]
scope_vars <- all_vars[1:ceiling(length(all_vars)/2)]
formula_full <- as.formula(paste0("a ~ ", paste(all_vars, collapse = " + ")))
mod0 <- gamlss(formula_full, data = dt, family = "NO", trace = FALSE)
res_i1 <- drop1All(object = mod0, scope = scope_vars, print = FALSE, parallel = ifelse(cores>1, "multicore", "no"), ncpus = cores)
Once I have done this, I can run also successfully the wrapper function
res_f2 <- fun.wrapper(dt = data, cores = 1)
I tried to several, mostly trial and error driven attempts to resolve this. I read about lexical scoping and closures since I strongly assume that the above drop1All call access the wrong data. I tried to assign and <<- the respective variables to the global environment. none of which did the trick.
Therefore I would be very happy if one of you could point me to a solution for this problem. thanks in advance.
sessionInfo()
R version 4.2.1 (2022-06-23)
Platform: x86_64-pc-linux-gnu (64-bit)
Running under: Ubuntu 20.04.4 LTS
Matrix products: default
BLAS: /usr/lib/x86_64-linux-gnu/blas/libblas.so.3.9.0
LAPACK: /usr/lib/x86_64-linux-gnu/lapack/liblapack.so.3.9.0
locale:
[1] LC_CTYPE=en_US.UTF-8 LC_NUMERIC=C
[3] LC_TIME=de_AT.UTF-8 LC_COLLATE=en_US.UTF-8
[5] LC_MONETARY=de_AT.UTF-8 LC_MESSAGES=en_US.UTF-8
[7] LC_PAPER=de_AT.UTF-8 LC_NAME=C
[9] LC_ADDRESS=C LC_TELEPHONE=C
[11] LC_MEASUREMENT=de_AT.UTF-8 LC_IDENTIFICATION=C
attached base packages:
[1] parallel splines stats graphics grDevices utils datasets
[8] methods base
other attached packages:
[1] gamlss_5.4-12 nlme_3.1-162 gamlss.dist_6.0-5 MASS_7.3-58
[5] gamlss.data_6.0-2 data.table_1.14.8
loaded via a namespace (and not attached):
[1] compiler_4.2.1 Matrix_1.5-3 survival_3.5-5 grid_4.2.1
[5] lattice_0.20-45