错误时是否使用tryCatch跳过循环的下一个值?

错误时是否使用tryCatch跳过循环的下一个值?,r,error-handling,exception-handling,try-catch,R,Error Handling,Exception Handling,Try Catch,我已经阅读了一些关于tryCatch和cuzzins的其他SO问题,以及文档: 但我还是不明白 我正在运行一个循环,如果出现以下几种错误中的任何一种,我想跳到下一步: for (i in 1:39487) { # EXCEPTION HANDLING this.could.go.wrong <- tryCatch( attemptsomething(), err

我已经阅读了一些关于
tryCatch
和cuzzins的其他SO问题,以及文档:

但我还是不明白

我正在运行一个循环,如果出现以下几种错误中的任何一种,我想跳到下一步:

for (i in 1:39487) {

  # EXCEPTION HANDLING
  this.could.go.wrong <- tryCatch(
                           attemptsomething(),
                           error=function(e) next
                         )
  so.could.this <- tryCatch(
                     doesthisfail(),
                     error=function(e) next
                   )

  catch.all.errors <- function() { this.could.go.wrong; so.could.this; }
  catch.all.errors;


  #REAL WORK
  useful(i); fun(i); good(i);

  }  #end for

我在这里遗漏了什么基本点?
tryCatch
显然在
for
循环中,那么为什么
R
不知道这一点呢?

使用
tryCatch
的关键是意识到它返回一个对象。如果
tryCatch
中存在错误,则此对象将从类
error
继承。您可以使用函数
inherit
测试类继承

x <- tryCatch(stop("Error"), error = function(e) e)
class(x)
"simpleError" "error"       "condition"  

函数
next
记录在`的

如果您想使用它,而不是将主工作例程放在
If
中,那么您的代码应该如下所示:

for (i in 1:39487) {
  #ERROR HANDLING
  possibleError <- tryCatch(
      thing(),
      error=function(e) e
  )

  if(inherits(possibleError, "error")) next

  #REAL WORK
  useful(i); fun(i); good(i);

}  #end for
for(i在1:39487中){
#错误处理

可能的错误我遗漏了一件事,很清楚,那就是:

  • next
    在函数内部不起作用
  • 您需要从函数内部(在我的例子中是
    tryCatch
    )向外部发送一些信号或标志(例如,
    Voldemort=TRUE
  • (这类似于在局部私有函数中修改全局公共变量)
  • 然后在函数外部,检查是否挥动了旗帜(伏地魔==TRUE
)。如果是这样,则在函数外部调用
break
next

    我所看到的唯一真正详细的解释可以在这里找到:

    下面是那篇博客文章的代码片段,展示了tryCatch是如何工作的

    #!/usr/bin/env Rscript
    # tryCatch.r -- experiments with tryCatch
    
    # Get any arguments
    arguments <- commandArgs(trailingOnly=TRUE)
    a <- arguments[1]
    
    # Define a division function that can issue warnings and errors
    myDivide <- function(d, a) {
      if (a == 'warning') {
        return_value <- 'myDivide warning result'
        warning("myDivide warning message")
      } else if (a == 'error') {
        return_value <- 'myDivide error result'
        stop("myDivide error message")
      } else {
        return_value = d / as.numeric(a)
      }
      return(return_value)
    }
    
    # Evalute the desired series of expressions inside of tryCatch
    result <- tryCatch({
    
      b <- 2
      c <- b^2
      d <- c+2
      if (a == 'suppress-warnings') {
        e <- suppressWarnings(myDivide(d,a))
      } else {
        e <- myDivide(d,a) # 6/a
      }
      f <- e + 100
    
    }, warning = function(war) {
    
      # warning handler picks up where error was generated
      print(paste("MY_WARNING:  ",war))
      b <- "changing 'b' inside the warning handler has no effect"
      e <- myDivide(d,0.1) # =60
      f <- e + 100
      return(f)
    
    }, error = function(err) {
    
      # warning handler picks up where error was generated
      print(paste("MY_ERROR:  ",err))
      b <- "changing 'b' inside the error handler has no effect"
      e <- myDivide(d,0.01) # =600
      f <- e + 100
      return(f)
    
    }, finally = {
    
      print(paste("a =",a))
      print(paste("b =",b))
      print(paste("c =",c))
      print(paste("d =",d))
      # NOTE:  Finally is evaluated in the context of of the inital
      # NOTE:  tryCatch block and 'e' will not exist if a warning
      # NOTE:  or error occurred.
      #print(paste("e =",e))
    
    }) # END tryCatch
    
    print(paste("result =",result))
    
    !/usr/bin/env Rscript
    #tryCatch.r——使用tryCatch的实验
    #有什么论据吗
    (i in-3:3)的参数
    {
    #错误处理
    
    可能错误我发现其他答案非常令人困惑。这里是一个非常简单的实现,适用于任何想在发生错误时直接跳到下一个循环迭代的人

    for (i in 1:10) {
    
      skip_to_next <- FALSE
    
      # Note that print(b) fails since b doesn't exist
    
      tryCatch(print(b), error = function(e) { skip_to_next <<- TRUE})
    
      if(skip_to_next) { next }     
    }
    
    for(1:10中的i){
    
    跳到下一个谢谢你的回答。我本来是像你建议的那样避免下一个的,但是当我想到越来越多可能被发现的错误时,代码变成了一堆括号:和“编程”一样糟糕或者更糟糕Excel单元格中的一系列条件。当我运行
    ?对于
    ,下一行是
    +
    (请求更多输入)@Andrie,如果函数为空,写
    error=function(e)
    有什么意义?这应该是其他东西的缩写吗?我的错误。应该是
    error=function(e)e
    。这将返回错误消息。我还在回答中添加了对该机制的解释。我很好奇,为什么您更喜欢避免“下一步”——无论是旧学校还是新学校,这通常被认为是良好的实践输入法。与“下一步被认为是有害的”非常不同事实上,这是非常有害的。但是循环控制操作符可以极大地简化代码并消除前哨变量,因为前哨变量往往有令人讨厌的边缘情况。正如@laotzi所指出的,你可以节省大量的括号和大括号。事实上,这是可能的,不是一种优雅的方式,但仍然是:最后!这么多复杂的解释。但在这里,你可以简化了整个过程,为社区做出了巨大的贡献。对于那些对
    
    
    #!/usr/bin/env Rscript
    # tryCatch.r -- experiments with tryCatch
    
    # Get any arguments
    arguments <- commandArgs(trailingOnly=TRUE)
    a <- arguments[1]
    
    # Define a division function that can issue warnings and errors
    myDivide <- function(d, a) {
      if (a == 'warning') {
        return_value <- 'myDivide warning result'
        warning("myDivide warning message")
      } else if (a == 'error') {
        return_value <- 'myDivide error result'
        stop("myDivide error message")
      } else {
        return_value = d / as.numeric(a)
      }
      return(return_value)
    }
    
    # Evalute the desired series of expressions inside of tryCatch
    result <- tryCatch({
    
      b <- 2
      c <- b^2
      d <- c+2
      if (a == 'suppress-warnings') {
        e <- suppressWarnings(myDivide(d,a))
      } else {
        e <- myDivide(d,a) # 6/a
      }
      f <- e + 100
    
    }, warning = function(war) {
    
      # warning handler picks up where error was generated
      print(paste("MY_WARNING:  ",war))
      b <- "changing 'b' inside the warning handler has no effect"
      e <- myDivide(d,0.1) # =60
      f <- e + 100
      return(f)
    
    }, error = function(err) {
    
      # warning handler picks up where error was generated
      print(paste("MY_ERROR:  ",err))
      b <- "changing 'b' inside the error handler has no effect"
      e <- myDivide(d,0.01) # =600
      f <- e + 100
      return(f)
    
    }, finally = {
    
      print(paste("a =",a))
      print(paste("b =",b))
      print(paste("c =",c))
      print(paste("d =",d))
      # NOTE:  Finally is evaluated in the context of of the inital
      # NOTE:  tryCatch block and 'e' will not exist if a warning
      # NOTE:  or error occurred.
      #print(paste("e =",e))
    
    }) # END tryCatch
    
    print(paste("result =",result))
    
    for (i in -3:3) {
      #ERROR HANDLING
      possibleError <- tryCatch({
        print(paste("Start Loop ", i ,sep=""))
        if(i==0){
          stop()
        }
      }
        ,
        error=function(e) {
          e
          print(paste("Oops! --> Error in Loop ",i,sep = ""))
        }
      )
      
      if(inherits(possibleError, "error")) next
    
      print(paste("  End Loop ",i,sep = ""))
      
    }
    
    for (i in 1:10) {
    
      skip_to_next <- FALSE
    
      # Note that print(b) fails since b doesn't exist
    
      tryCatch(print(b), error = function(e) { skip_to_next <<- TRUE})
    
      if(skip_to_next) { next }     
    }