我想在for
循環內迭代地擬合lmer()
模型並存儲結果。當我遇到錯誤時,我不希望merMod
對象(lmer()
模型的輸出)覆蓋上一次迭代中的merMod
對象。例如:使用tryCatch()但在遇到錯誤/警告時不覆蓋對象
# install.packages(c("lme4", "dplyr", "ggplot2"), dependencies = TRUE)
library("lme4")
library("dplyr")
library("ggplot2")
predList <- list()
j <- 1
for(i in 2:9){
tr <- sleepstudy %>% filter(Days < i)
pr <- sleepstudy %>% filter(Days == i)
fm <- tryCatch({lmer(Reaction ~ Days + (1|Subject), data=sleepstudy)},
warning = function(w) {#Code to move along to `predict` without overwriting `fm`},
error = function(e) {#Code to move along to `predict` without overwriting `fm`})
#predict the Reaction
pr$prRe <- predict(fm, pr)
predList[[j]] <- pr
j = j + 1
}
pred <- bind_rows(predList) %>% arrange(Subject, Days)
ggplot(data=pred, aes(Reaction, prRe)) + geom_point()
此代碼實際上沒有問題。但是,讓我們假設當i=4
,我從lmer()
得到一個錯誤。發生這種情況時,我不想用錯誤消息替換fm
。相反,我只想離開fm
(從i=3
開始的模型輸出),並移動到lmer()
之後的predict
聲明。我怎樣才能做到這一點?
特殊情況可能是第一次迭代失敗時。我們不用擔心這一點。假設循環的第一次迭代總是成功地適合lmer()
模型。
一種解決方案可能會做這樣的事情:
# install.packages(c("lme4", "dplyr", "ggplot2"), dependencies = TRUE)
library("lme4")
library("dplyr")
library("ggplot2")
predList <- list()
j <- 1
for(i in 2:9){
tr <- sleepstudy %>% filter(Days < i)
pr <- sleepstudy %>% filter(Days == i)
fm <- tryCatch({lmer(Reaction ~ Days + (1|Subject), data=sleepstudy)},
warning = function(w) {message(w)},
error = function(e) {message(e)})
#If model did not fail, predict as usual and store fm in fm0. If model did fail, use fm0 from previous iteration for prediction
if(is.null(fm)){
pr$prRe <- predict(fm0, pr)
} else
{fm0 <- fm
pr$prRe <- predict(fm, pr)
}
predList[[j]] <- pr
j = j + 1
}
但是,這是一個有點冗長。有什麼簡單的我可以在tryCatch()
函數中簡單地不覆蓋fm
並在模型失敗時轉到下一個語句?
謝謝!很簡單的解決方案PS:我有'i'和'j'的原因是在我的實際分析中,我正在迭代'Week'。數據從'Week = 1'開始,到'Week = 567'結束。但是,我的數據中只有450個「Week」的唯一值。因此,沿着從1,...的方式,超過100個值的567缺失。我可以在數據中創建一個單獨的變量:'j = 1,...,450',但我認爲'i'和'j'指數同樣簡單。謝謝! – hossibley
好的很高興提供幫助。記得投票並接受答案,如果它幫助:) – latorrefabian