Ho un problema strano con R che non riesco a capire.Errore oggetto non trovato quando si passa la formula del modello a un'altra funzione
Ho provato a scrivere una funzione che esegue la convalida incrociata K-fold per un modello scelto dalla procedura stepwise in R. (Sono a conoscenza dei problemi con procedure stepwise, è puramente a scopo di confronto) :)
Ora il problema è che, se definisco i parametri della funzione (linmod, k, direzione) ed eseguo il contenuto della funzione, funziona perfettamente. MA, se lo eseguo come una funzione, ottengo un errore che dice che l'oggetto datas.train non può essere trovato.
Ho provato a passare attraverso la funzione con debug() e l'oggetto esiste chiaramente, ma R dice che non funziona quando eseguo effettivamente la funzione. Se ho appena adattato un modello usando lm() funziona bene, quindi credo che sia un problema con la funzione passo nel ciclo, mentre all'interno di una funzione. (Provate commentando il comando passo, e impostare le previsioni a quelle del modello lineare ordinario.)
#CREATE A LINEAR MODEL TO TEST FUNCTION
lm.cars <- lm(mpg~.,data=mtcars,x=TRUE,y=TRUE)
#THE FUNCTION
cv.step <- function(linmod,k=10,direction="both"){
response <- linmod$y
dmatrix <- linmod$x
n <- length(response)
datas <- linmod$model
form <- formula(linmod$call)
# generate indices for cross validation
rar <- n/k
xval.idx <- list()
s <- sample(1:n, n) # permutation of 1:n
for (i in 1:k) {
xval.idx[[i]] <- s[(ceiling(rar*(i-1))+1):(ceiling(rar*i))]
}
#error calculation
errors <- R2 <- 0
for (j in 1:k){
datas.test <- datas[xval.idx[[j]],]
datas.train <- datas[-xval.idx[[j]],]
test.idx <- xval.idx[[j]]
#THE MODELS+
lm.1 <- lm(form,data= datas.train)
lm.step <- step(lm.1,direction=direction,trace=0)
step.pred <- predict(lm.step,newdata= datas.test)
step.error <- sum((step.pred-response[test.idx])^2)
errors[j] <- step.error/length(response[test.idx])
SS.tot <- sum((response[test.idx] - mean(response[test.idx]))^2)
R2[j] <- 1 - step.error/SS.tot
}
CVerror <- sum(errors)/k
CV.R2 <- sum(R2)/k
res <- list()
res$CV.error <- CVerror
res$CV.R2 <- CV.R2
return(res)
}
#TESTING OUT THE FUNCTION
cv.step(lm.cars)
Qualche idea?
Sembra che ci sia un problema di scoping, dove 'step (lm.1, direzione = direzione, tracce = 0)' 'non riesce a trovare datas.train', come già sapete. Non riesco a vedere la causa del problema da solo. Assegnare 'datas.train' come variabile globale è un work-around, ma non particolarmente soddisfacente (' datas.train << - datas [-xval.idx [[j]],] '). Forse questo dovrebbe essere migrato a StackOverflow? – jthetzel
In particolare, la chiamata a 'ADD1 (in forma, la portata $ aggiungere, scale = scala, tracce = traccia, k = k, ...)' 'in fase()' genera l'errore, dove 'ADD1()' è ' statistiche ::: add1.lm'. – jthetzel
@jthetzel, infatti. In un modo ho risolto un problema simile, ma per un'altra chiamata di funzione all'interno di un ciclo dovevo assegnarlo globalmente. – dcl