【问题标题】:error: 'object not found' in nested functions错误:嵌套函数中的“找不到对象”
【发布时间】:2015-04-20 12:53:19
【问题描述】:

我正在使用logistf::logistflogistf::forward 函数编写函数。我将在这里给出一个使用logistf 包中的sex2 的最小工作示例。

data(sex2)
fwSel <- function(datamod) {
  fitnull <- logistf(case ~ 1, data = datamod, pl = FALSE) 
  fw <- forward(fitnull)
  return(fw)
}
fwSel(sex2)

我得到以下输出:

步骤 0:启动模型

is.data.frame(data) 中的错误:找不到对象“datamod”。

有人解释一下吗?

【问题讨论】:

    标签: r function logistf


    【解决方案1】:

    这是您可以在 R 中遇到的典型错误。它已被再次询问,不幸的是,它根据不同函数在不同环境中的工作方式以及函数如何根据 parent.env 或 @ 的使用尝试查找数据而发生987654324@。这可能是两个问题之一:

    • 惰性求值问题:
      尝试在您的 logistf 函数之前使用 force(datamod),因为您的 datamod 当前未在您的自定义函数中进行评估。如果存在以下问题,这可能不起作用:
    • 您的 datamod 数据集存在于函数的执行环境中。如果函数链中的某个函数使用对parent.frame() 的调用或对parent_env() 的调用,这将导致问题,因为R 在不同环境中查找数据的方式不同。解决此问题的唯一方法是在全局环境中启动 datamod,即:

    data(sex2)
    datamod <- sex2
    fwSel <- function(datamod) {
        fitnull <- logistf(case ~ 1, data = datamod, pl = FALSE) 
        fw <- forward(fitnull)
        return(fw)
    }
    fwSel(sex2)
    

    这肯定会起作用,因为无论如何都会搜索全局环境。

    我发现link 是了解parent.envparent.frame 的不同之处以及使用这两个内部函数如何导致您所面临的问题的绝佳方式。

    我根据链接中的函数制作了一个新示例,可以准确地演示您的问题:

    f = function() {
      print(c(f=environment(), defined_in=parent.env(environment()),  
        called_from=parent.frame()))
    
      #search for mydata in calling environment
      try(print(get('mydata',env=parent.frame())))  
    
      #search for mydata in parent evnironment
      try(print(get('mydata',env=parent.env(environment())))) 
      }
    
    g = function() {
      mydata <- c(1,2,3)
      print(c(g=environment(), f()))
      }   
    
    > g()
    $f
    <environment: 0x0000000030868df8>
    
    $defined_in
    <environment: R_GlobalEnv>
    
    $called_from
    <environment: 0x000000003086a360>
    
    #the first get works perfect
    [1] 1 2 3       
    
    #the second produces an error
    Error in get("mydata", env = parent.env(environment())) : 
      object 'mydata' not found
    
    $g
    <environment: 0x000000003086a360>
    

    正如您在上面看到的,在调用环境中使用get 是有效的,而在父环境中使用get 会失败并产生错误。这也是(可能)在您的函数中发生的情况。

    【讨论】:

    • +1 为这个出色的解释!它与启动“datamod”一起使用,或者更确切地说将参数datamod 重命名为sex2
    • 感谢您的客气话 :)。真的很高兴它很有帮助。老实说,即使对于开发人员来说,环境有时也会变得棘手。如果您有时间了解环境的工作原理,我建议您阅读this。它绝对帮助了我:)
    猜你喜欢
    • 2012-03-12
    • 2018-08-29
    • 1970-01-01
    • 1970-01-01
    • 2019-01-18
    • 2011-10-20
    • 1970-01-01
    • 1970-01-01
    • 2013-06-22
    相关资源
    最近更新 更多