R:承诺已经在评估中

时间:2013-06-26 02:59:47

标签: r lazy-evaluation callstack

我知道你可能又厌倦了再次回答同样的问题,但我仍然在several other questions中讨论了错误:

  

承诺已经在评估中:递归默认参数引用或早期问题?

即使我确实遵循了前置"."

的“繁琐”建议
show.large.objects.threshold <- 100000
show.large.objects.exclude <- c("closure")
show.large.objects <- function (.envir = sys.frame(),
                                threshold = show.large.objects.threshold,
                                exclude = show.large.objects.exclude) {
  for (n in print(ls(.envir, all.names = TRUE))) tryCatch({
    o <- get(n,envir = .envir)
    s <- object.size(o)
    if (s > threshold && !(typeof(o) %in% exclude)) {
      cat(n,": ")
      print(s,units="auto")
    }
  }, error = function(e) { cat("n=",n,"\n"); print(e) })
}
show.large.objects.stack <- function (.threshold = show.large.objects.threshold,
                                      skip.levels = 1,# do not examine the last level - this function
                                      .exclude = show.large.objects.exclude) {
  for (level in 1:(sys.nframe()-skip.levels)) {
    cat("*** show.large.objects.stack(",level,") ")
    print(sys.call(level))
    show.large.objects(.envir = sys.frame(level), threshold = .threshold, exclude = .exclude)
  }
}

但我仍然遇到错误:

> f <- function () { c <- 1:1e7; d <- 1:1e6; print(system.time(show.large.objects.stack())) }
> f()
*** show.large.objects.stack( 1 ) f()
[1] "c" "d"
c : 38.1 Mb
d : 3.8 Mb
*** show.large.objects.stack( 2 ) print(system.time(show.large.objects.stack()))
[1] "..." "x"  
n= ... 
<simpleError in get(n, envir = .envir): argument "..." is missing, with no default>
n= x 
<simpleError in get(n, envir = .envir): promise already under evaluation: recursive default argument reference or earlier problems?>
*** show.large.objects.stack( 3 ) system.time(show.large.objects.stack())
[1] "expr"    "gcFirst" "ppt"     "time"   
n= expr 
<simpleError in get(n, envir = .envir): promise already under evaluation: recursive default argument reference or earlier problems?>
          user         system        elapsed 
    0 (0.00ms)     0 (0.00ms) 0.002 (2.00ms) 
  1. 那么,我还有什么问题呢?
  2. 真的需要.中的.envir吗?那么.exclude.threshold呢?
  3. 为什么我会收到argument "..." is missing, with no default错误?
  4. 为什么我会收到promise already under evaluation错误?
  5. 谢谢!

1 个答案:

答案 0 :(得分:3)

当调用f时,5个级别的堆栈构建为show.large.objects,它开始从顶部开始评估帧的内容。

f
  -> print
     -> system.time
        -> show.large.objects.stack
           -> show.large.objects

1级

f()

这里的一切都还可以。

等级2

print(system.time(show.large.objects.stack()))

当你在其框架上调用ls(.envir, all.names)时,你会得到

[1] "..." "x"  

其中...缺失并在您上面调用get时抛出错误3,并且当前正在评估x = system.time(show.large.objects.stack())并抛出错误4。

等级3

system.time(show.large.objects.stack())

ls给你

[1] "expr"    "gcFirst" "ppt"     "time"   

其中expr = show.large.objects.stack()目前仍在评估中,并引发另一个错误4。

等级4

show.large.objects.stack()

ls不包含任何粗略的内容,并且没有错误地完成。

底线

show.large.frames()必须是evalutad,不能作为任何函数的参数,否则会抛出错误。为什么不让它自己进行打印?

我发现这非常有用

> debug(show.large.objects)
> f()
Browse[2]> lapply(sys.frames(), ls)
[[1]]
[1] "c" "d"

[[2]]
[1] "x"

[[3]]
[1] "expr"    "gcFirst" "ppt"     "time"   

[[4]]
[1] "level"       "skip.levels"

[[5]]
[1] "exclude"   "threshold"