1

这似乎是一个奇怪的问题,但我确实有一个我正在尝试弄清楚的用例。

假设我正在编写一个包,并且我有一个函数,我想允许用户使用其他名称 - 用户提供函数的名称。我想知道实现这一目标的最佳方法是什么?

#' @export
foo <- function() "Hello"
#' @export
addAlias <- function(x) assign(x, foo, envir = globalenv())

这是我想要得到的行为 - 现在用户可以调用addAlias("bar"),然后如果他调用bar()它,就好像他调用了我的函数。

显然这不是一个好的解决方案,因为它分配给全局环境。有没有人对什么是最好的方法有反馈?我试过的几种方法:

1.分配给globalenv

就像我在示例中展示的那样。这似乎奏效了。

2.分配到包的环境

addAlias <- function(x) assign(x, foo, as.environment("package:mypackage"))

这工作了一段时间,直到我意识到它只适用于devtools而不是如果包由于锁定环境而正确加载

3. 将新环境附加到搜索路径

.onLoad <- function(libname, pkgname) {
  assign("aliases", new.env(), envir = parent.env(environment()))
  attach(aliases)
  invisible()
}

addAlias <- function(x) assign(x, foo, aliases)

这是我不喜欢的,因为使用attach. 在这种情况下是否有保证?我什么时候detach

4. 暴露一个单独的命名环境

#' @export
#' @keywords internal
aliases <- new.env()

addAlias <- function(x) assign(x, foo, aliases)

bar()这可行,但用户需要调用alises$bar()or ,而不是能够调用mypackage::aliases$bar()。我不喜欢那样,但这是一个有趣的实验。我也不知道这样导出变量是否可以?

任何帮助表示赞赏

4

1 回答 1

1

我认为更合适的方式是使用闭包

#' @export
foo <- function() "Hello"
#' @export
getfoo <- function() {
    function(){
        # do anything, including running foo()
        foo()
    }
}

有了这个,你可以做

> bar <- getfoo()
> bar()
[1] "Hello"
于 2015-04-25T06:48:50.683 回答