我正在尝试使用主函数作为主力来适应多个不同的模型(每个函数都使用变量
model
作为字符串来调用此主函数,并通过 ...
传递所需的参数)
对于
model = "loess"
和 model = "glm"
效果很好,但对于 model = "gam"
则失败。具体来说,除非我使用命名空间对函数名称进行硬编码,否则 do.call(model, args)
将会失败。但我需要 model
是一个变量。同样的问题也发生在我用来获取 formalArgs
的 args
上。例如(reprex)基于类似SO问题的建议:
model <- "mgcv::gam"
formalArgs(mgcv::gam) # Works but function is hard-coded
formalArgs(gam) # Fails
formalArgs(model) # Fails
formalArgs(eval(model)) # Fails
formalArgs(substitute(model)) # Returns NULL with warning
formalArgs(deparse(substitute(model))) # Fails
错误消息是
Error in get(fun, mode = "function", envir = envir) : object '"mgcv::gam"' of mode 'function' was not found
(或者在替换的情况下,返回 NULL)。
如果将
model
更改为 "glm"
或 "loess"
,则 formalArgs(model)
和 formalArgs(eval(model))
可以工作。
我认为这与这两个函数都来自基本
stats
包有关,而 gam
则不是。但如何解决呢?
问题在于
"mgcv::gam"
是表达式的文本,而不是函数的名称。函数名称是"gam"
。
要检索形式,您可以使用
formalArgs(x)
,其中 x
是搜索列表中可用的函数的名称,或实际的函数对象。
这就是
formalArgs(mgcv::gam)
起作用的原因,因为该表达式检索函数对象。其他方法可以做到这一点是
model <- mgcv::gam
formalArgs(model)
#> [1] "formula" "family" "data"
#> [4] "weights" "subset" "na.action"
#> [7] "offset" "method" "optimizer"
#> [10] "control" "scale" "select"
#> [13] "knots" "sp" "min.sp"
#> [16] "H" "gamma" "fit"
#> [19] "paraPen" "G" "in.out"
#> [22] "drop.unused.levels" "drop.intercept" "nei"
#> [25] "discrete" "..."
model <- "mgcv::gam"
obj <- eval(parse(text = model))
formalArgs(obj)
#> [1] "formula" "family" "data"
#> [4] "weights" "subset" "na.action"
#> [7] "offset" "method" "optimizer"
#> [10] "control" "scale" "select"
#> [13] "knots" "sp" "min.sp"
#> [16] "H" "gamma" "fit"
#> [19] "paraPen" "G" "in.out"
#> [22] "drop.unused.levels" "drop.intercept" "nei"
#> [25] "discrete" "..."
创建于 2023-10-03,使用 reprex v2.0.2