将“curve”与列表中的函数一起使用

Maë*_*aël 2 plot curve r function list

为什么似乎curve不适用于从列表中提取的元素?

考虑两个看似相同但构建方式不同的函数:

a <- function(value){
  function(x) x + value
}

m <- lapply(1:3, a)
f <- a(1)
all.equal(f, m[[1]])
#[1] TRUE
Run Code Online (Sandbox Code Playgroud)

curve适用于f,但不适用于m[[1]]

> curve(m[[1]])
Error in curve(m[[1]]) : 
  'expr' must be a function, or a call or an expression containing 'x'
Run Code Online (Sandbox Code Playgroud)

但如果之前提取了对象,它就会起作用:

d <- m[[1]]
curve(d)
Run Code Online (Sandbox Code Playgroud)

这是有原因的吗?

Ben*_*ker 5

curve()是一个“神奇”函数,在可能的情况下尝试将其输入解释为表达式;它并不总是有效。

@user2554330 期待的评论curve()(来自?curve):

函数的名称,或者作为函数编写的调用或表达式,其x计算结果将是与 长度相同的对象x

相反,m[[1]]是一个计算结果为函数 的表达式。相反,d是函数的名称。您可以使用curve(m[[1]](x))将输入写为 x 函数的表达式来获得所需的内容。

在下面的代码中,R 查看传递给的表达式curve()并询问是否is.name(sexpr)为 TRUE。该测试通过了f但失败了m[[1]](如果您想在函数上下文之外测试它,则需要比较is.name(quote(f))is.name(quote(m[[1]]))。

奇怪的是,它plot(m[[1]]) 确实有效(它调用plot.function(),它curve()在内部使用不同的参数进行调用)。

sexpr <- substitute(expr)
if (is.name(sexpr)) {
    expr <- call(as.character(sexpr), as.name(xname))
}
else {
    if (!((is.call(sexpr) || is.expression(sexpr)) && xname %in% 
        all.vars(sexpr))) 
        stop(gettextf("'expr' must be a function, or a call or an expression containing '%s'", 
            xname), domain = NA)
    expr <- sexpr
}
Run Code Online (Sandbox Code Playgroud)