【问题标题】:Recursive S3 calls in a package包中的递归 S3 调用
【发布时间】:2017-12-07 15:52:27
【问题描述】:

我想要完成的事情

我有一个 R 包,其中包含一些以递归方式使用的内部 R 函数(在下面的示例中称为 f 和 g)。在最小示例中,函数只返回其参数的长度,但在实际代码中,它们会触发更复杂的计算。

我想做的是:

  1. 如果用户将对象传递给函数 g,R 应该查找我们是否有可以调用此对象的 S3 方法。

  2. 如果对象是一个列表,函数 g 应该应用于列表中的每个对象。如果我们还没有达到最大递归深度,请转到 1。如果我们达到最大递归级别,请停止。

显示问题的代码

将以下代码放入包中很重要。我得到的错误只有在代码是包的一部分时才能重现。

utils.R

g <- function(x, depth = 0) {
  stopifnot(depth <= 1)
  UseMethod("g")
}

g.numeric <- function(x, depth = 0) {
  length(x)
}

g.integer <- function(x, depth = 0) {
  length(x)
}

g.double <- function(x, depth = 0) {
  length(x)
}

g.list <- function(x, depth = 0) {
  sum(sapply(x, g, depth = depth + 1))
}

core.R

#' @export
core_fun <- function(x) {
  g(x)
}

我的期望

错误

结果应该是 6;

x <- c(1.0, 1.3, 1.5)
core_fun(list(x,x))

但我收到一条错误消息:

Error in UseMethod("g") : 
no applicable method for 'g' applied to an object of class "c('double','numeric')"  

通过

结果应该是 3。

x <- c(1.0, 1.3, 1.5)
core_fun(x)

备注

当我调用示例时失败了,在将函数 g 加载到全局命名空间后,我得到了预期的结果,6。

所以我认为这是一个与命名空间/S3 相关的问题,但我不知道如何解决它。

【问题讨论】:

    标签: r recursion r-package r-s3


    【解决方案1】:

    我相信这与?lapply 中的这个注释有关。如果您按照他们的建议使用包装器运行它,则调度已正确完成。

    g.list <- function(x, depth = 0) {
      sum(sapply(x, function(x_i) g(x_i, depth = depth + 1)))
    }
    

    【讨论】:

      猜你喜欢
      • 2010-10-18
      • 2019-10-18
      • 2011-09-16
      • 2016-03-21
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多