0

我如何做到这一点R

我已经采购了一个具有某些名称的函数exampleFoo假设:

exampleFoo <- function(a, predefined, signature)

给定字符向量exampleFoo,我如何使用它来调用具有该名称的函数?

4

3 回答 3

4

这取决于这是在另一个函数内部还是在顶层进行。我会按照相反的顺序来处理。

exampleFoo <- function(a, predefined, signature) {
   1:10
}

FUN <- "exampleFoo"

get(FUN)
get(FUN)()

> get(FUN)
function(a, predefined, signature) {
   1:10
}
> get(FUN)()
 [1]  1  2  3  4  5  6  7  8  9 10

在函数中,match.fun参数在这里最适用。get查找提供给它的名称的对象,而match.fun在搜索时只考虑函数对象。这有一个额外的好处,那就是不匹配可能具有相同名称的非功能对象。

FOO <- function(f) {
  BAR <- match.fun(f)
  BAR()
}

> FOO(FUN)
 [1]  1  2  3  4  5  6  7  8  9 10
> FOO("exampleFoo")
 [1]  1  2  3  4  5  6  7  8  9 10

您不能match.fun在顶层使用(容易?),因为它旨在在调用者的父框架中执行匹配,并且全局环境没有父 (IIRC)。

其他例子

@agstudy 提出了一种switch基于方法的包装函数,该函数可以按名称调用多个预定义函数之一。在评论中,我提出了两个更简单的替代方案。在这里,我对此进行了扩展:

foo1 <- function(method, ...) {
  dots <- list(...)
  FUN <- match.fun(method)
  do.call(FUN, dots)
} 

或者

foo2 <- function(method = c("fun1", "fun2", "fun3"), ...) {
  dots <- list(...)
  method <- match.arg(method)
  FUN <- match.fun(method)
  do.call(FUN, dots)
}

我把这些写成非常通用的函数,可以接受任何参数加上method. 如果由 / 传递的函数引用method...参数,则可以直接调用这些函数,可能带有一个或多个命名参数,例如

## assuming `method` refers to a function with a first argument `x` and also
##   a `...` argument
foo3 <- function(method, x, ...) {
  FUN <- match.fun(method)
  FUN(x, ...)
}
于 2013-04-05T15:19:05.643 回答
1
text<-"exampleFoo"
exampleFoo<-function(x) print("Success")
eval(parse(text=paste(text,"()")))
#[1] "Success" 

正如@joran 建议get()的那样,似乎可以替代eval(parse(text="..."))

get(text)()
#[1] "Success"
于 2013-04-05T14:50:21.410 回答
1

我会用switch这个,比如:

algoFactory <- function (method = c("algo1", "alog2", 
                                   "algo3")
{
  method = method[1]
  switch(method, algo1 = {
  res = algo1.Impl(...)
}, algo2 = {
  res = algo2.Impl(...)
}, algo3 = {
  res = algo3.Impl(...)
})}

每次我添加一个新算法时,我都会更新这个主函数。在您的 RscripT 中,您将其称为例如:

 Rscript  algoFactory.R 'algo1'
于 2013-04-05T14:55:17.503 回答