4

我有一个关于sapplyR 的问题。在我的示例中,我将其用于留一交叉验证

 ##' Calculates the LOO CV score for given data and regression prediction function
##'
##' @param reg.data: regression data; data.frame with columns 'x', 'y'
##' @param reg.fcn:  regr.prediction function; arguments:
##'                    reg.x: regression x-values
##'                    reg.y: regression y-values
##'                    x:     x-value(s) of evaluation point(s)
##'                  value: prediction at point(s) x
##' @return LOOCV score
loocv <- function(reg.data, reg.fcn)
{
  ## Help function to calculate leave-one-out regression values
  loo.reg.value <- function(i, reg.data, reg.fcn)
    return(reg.fcn(reg.data$x[-i],reg.data$y[-i], reg.data$x[i]))

  ## Calculate LOO regression values using the help function above
  n <- nrow(reg.data)
  loo.values <- sapply(seq(1,n), loo.reg.value, reg.data, reg.fcn)

  ## Calculate and return MSE
  return(???)
}

我的问题sapply如下:

  1. 我可以使用多个参数和函数吗,即sapply(X1,FUN1,X2,FUN2,..)X1分别是函数和X2函数的函数参数。FUN1FUN2
  2. 在上面的代码中,我应用1:n到了函数loo.reg.value。但是,这个函数有多个参数,实际上是 3 个:整数i、回归数据reg.data和回归函数reg.fcn。如果 sapply 中的函数有多个参数,并且我X只涵盖一个参数,那么 sapply 是否将其用作“第一个参数”?所以它会和sapply(c(1:n,reg.data,reg.fcn),loo.reg.value, reg.data, reg.fcn)?

感谢您的帮助

4

2 回答 2

2

在回答第一个问题时,是的,您可以使用多个函数,但是需要将第二个和后续函数传递给第一个函数,然后再传递给下一个函数等。因此,需要对函数进行编码以便接受额外的参数把它们传下去。

例如

foo <- function(x, f1, ...) f1(x, ...)
bar <- function(y, f2, ...) f2(y, ...)
foobar <- function(z, f3, ...) f3(z)

sapply(1:10, foo, f1 = bar, y = 2, f2 = foobar, z = 4, f3 = seq_len)

> sapply(1:10, foo, f1 = bar, y = 2, f2 = foobar, z = 4, f3 = seq_len)
     [,1] [,2] [,3] [,4] [,5] [,6] [,7] [,8] [,9] [,10]
[1,]    1    1    1    1    1    1    1    1    1     1
[2,]    2    2    2    2    2    2    2    2    2     2
[3,]    3    3    3    3    3    3    3    3    3     3
[4,]    4    4    4    4    4    4    4    4    4     4

这是一个愚蠢的例子,但它展示了如何将额外的参数传递给foo()最初,作为 的...参数的一部分sapply()。它还展示了如何让foo()函数和后续函数接受额外的参数传递,只需通过...函数定义中的使用以及如何调用下一个函数,例如f2(y, ...). 请注意,我还避免了位置匹配问题,并将提供给foo().

关于问题2,我认为你解释它的方式过于复杂。例如,您在 R 用 迭代的内容中复制了reg.dataand位,这是不正确的(这意味着您迭代了 vector 中的 3 个东西,而不是 over )。reg.fcnsapply()c(1:n,reg.data,reg.fcn)1:n

sapply(1:n, fun, arg1, arg2)相当于

fun(1, arg1, arg2)
fun(2, arg1, arg2)
....
fun(10, arg1, arg2)

同时sapply(1:n, fun, arg1 = bar, arg2 = foobar)相当于

fun(1, arg1 = bar, arg2 = foobar)
fun(2, arg1 = bar, arg2 = foobar)
....
fun(10, arg1 = bar, arg2 = foobar)
于 2013-07-23T15:39:53.550 回答
1

您传递给的函数sapply可以接受任意数量的参数(当然是在合理范围内),但它会为每个应用程序回收除第一个参数之外的所有参数。您是否尝试过运行此代码?看起来它会起作用。

于 2013-07-23T15:37:49.933 回答