R语言自定义函数中glm()公式的作用域与非标准评估报错解决办法
问题原因
glm()评估公式变量时,优先查找你传入的data参数(也就是示例中的DF2),找不到的话会去公式本身所属的环境查找。你调用函数时传入的formula = y ~ x + a + b是在全局环境定义的,全局环境里没有直接叫y、x的对象,因此触发报错。
修复方案1:合并变量到建模数据集(最推荐)
直接把传入的x、y和给定的data合并成新的建模数据集,glm()直接从合并后的数据里找所有变量,完全规避作用域问题,代码稳定性更强,后续做模型预测、诊断也不会因为环境丢失出问题:
fun <- function(x, y, formula = y ~ x, data = NULL) { out <- list() out$tab <- table(x, y) # 合并x、y到传入的data中,列名和公式里的x、y对应 model_data <- cbind(data.frame(y = y, x = x), data) out$mod <- glm(formula = formula, family = binomial, data = model_data) out }
原来的调用代码不需要任何修改即可正常运行:
# 测试调用 res <- fun(x = DF1$x, y = DF1$y, formula = y ~ x + a + b, data = DF2) # 查看模型结果 summary(res$mod)
修复方案2:修改公式的所属环境
如果不想合并数据集,可以把传入公式的环境设置为函数的当前环境,这样glm()在data里找不到变量时,就会到函数内部查找x、y参数:
fun <- function(x, y, formula = y ~ x, data = NULL) { out <- list() out$tab <- table(x, y) # 重设公式的环境为当前函数环境 environment(formula) <- environment() out$mod <- glm(formula = formula, family = binomial, data = data) out }
内容的提问来源于stack exchange,提问作者Thomas
相关产品推荐
相关产品推荐

