2010-04-12 51 views
94

有沒有人有R中異常處理的例子/教程?官方文件非常簡潔。R中的異常處理

+1

這也是一個很好的例子:http://stackoverflow.com/q/12193779/2026975。 – imriss 2013-08-14 17:44:35

+0

我發現這篇博文很有用:[http://mazamascience.com/WorkingWithData/?p=912](http://mazamascience.com/WorkingWithData/?p=912) – 2015-06-02 13:05:32

+0

我請求了SO文檔主題對於這個問題。 – Leonid 2017-06-01 05:41:40

回答

30

除了Shane的回答指向其他StackOverflow討論,您可以嘗試代碼搜索功能。這種原始的回答指出,谷歌的代碼搜索已經被停產,但你可以嘗試

只是爲了記錄在案,也有trytryCatch可能是可取的。我在Google代碼搜索中嘗試過很快計數,但是嘗試爲動詞本身獲取太多誤報 - 但看起來tryCatch更爲廣泛。

+0

也許這個例子可以幫助:[http://stackoverflow.com/a/12195574/2026975](http://stackoverflow.com/a/12195574/2026975) – imriss 2013-06-27 14:12:22

+0

A [Github搜索](https:// github。 com/search?q = tryCatch + language%3AR&type = Code&ref = searchresults)可能是不存在鏈接的替代品。 – Gregor 2014-04-13 03:29:28

58

基本上你想使用tryCatch()函數。查看幫助(「tryCatch」)瞭解更多詳情。

這裏有一個簡單的例子(記住,你可以做任何你想要的一個錯誤):

vari <- 1 
tryCatch(print("passes"), error = function(e) print(vari), finally=print("finished")) 
tryCatch(stop("fails"), error = function(e) print(vari), finally=print("finished")) 

看一看這些相關的問題:

+1

第三個鏈接不是鏈接。 – Marek 2010-04-13 12:04:51

+8

非Shane的錯 - 可以說是正則表達式中的一個錯誤,用於確定如何標記SO上的內容。 – 2010-04-13 12:18:39

7

重新啓動功能在從Lisp繼承的R中非常重要。如果你想在循環體中調用一些函數,並且你只是希望程序在函數調用崩潰的時候繼續,那麼這很有用。試試這個代碼:

for (i in 1:20) withRestarts(tryCatch(
if((a <- runif(1))>0.5) print(a) else stop(a), 
finally = print("loop body finished!")), 
abort = function(){}) 
6

函數trycatch()是相當直接的,並且有很多很好的教程。錯誤R中處理的優異的解釋可在哈德利韋翰的書Advanced-R被找到,接下來就是非常基本介紹到withCallingHandlers()withRestarts()在爲幾句話越好:

比方說一個低水平程序員編寫一個函數來計算絕對值 的值。他不知道如何來計算的話,但是他知道how to construct an error和 努力傳達自己的幼稚:

low_level_ABS <- function(x){ 
    if(x<0){ 
     #construct an error 
     negative_value_error <- structure(
        # with class `negative_value` 
        class = c("negative_value","error", "condition"), 
        list(message = "Not Sure what to with a negative value", 
         call = sys.call(), 
         # and include the offending parameter in the error object 
         x=x)) 
     # raise the error 
     stop(negative_value_error) 
    } 
    cat("Returning from low_level_ABS()\n") 
    return(x) 
} 

一箇中等水平的程序員也寫一個函數來計算絕對值,利用了遠遠不完全low_level_ABS功能。他知道,低級代碼拋出一個negative_value 錯誤時的x值爲負並表明一個解決問題的辦法,通過 建立restart,其允許mid_level_ABS用戶控制 方式,其中mid_level_ABS復甦(或不)從negative_value錯誤。

mid_level_ABS <- function(y){ 
    abs_y <- withRestarts(low_level_ABS(y), 
          # establish a restart called 'negative_value' 
          # which returns the negative of it's argument 
          negative_value_restart=function(z){-z}) 
    cat("Returning from mid_level_ABS()\n") 
    return(abs_y) 
} 

最後,高電平編程器使用mid_level_ABS函數來計算 絕對值,並建立了一個條件處理程序,它告訴 mid_level_ABS通過使用重啓 處理程序從negative_value錯誤恢復。

high_level_ABS <- function(z){ 
    abs_z <- withCallingHandlers(
      # call this function 
      mid_level_ABS(z) , 
      # and if an `error` occurres 
      error = function(err){ 
       # and the `error` is a `negative_value` error 
       if(inherits(err,"negative_value")){ 
        # invoke the restart called 'negative_value_restart' 
        invokeRestart('negative_value_restart', 
            # and invoke it with this parameter 
            err$x) 
       }else{ 
        # otherwise re-raise the error 
        stop(err) 
       } 
      }) 
    cat("Returning from high_level_ABS()\n") 
    return(abs_z) 
} 

所有這一切的一點是,通過使用withRestarts()withCallingHandlers(),功能 high_level_ABS能告訴mid_level_ABS如何從錯誤中恢復 不停止的 mid_level_ABS執行,這是每個人所low_level_ABS錯誤引發你不能做tryCatch()

> high_level_ABS(3) 
Returning from low_level_ABS() 
Returning from mid_level_ABS() 
Returning from high_level_ABS() 
[1] 3 
> high_level_ABS(-3) 
Returning from mid_level_ABS() 
Returning from high_level_ABS() 
[1] 3 

在實踐中,low_level_ABS代表一個函數,mid_level_ABS調用 很多(甚至可能是數百萬次),對此,錯誤 的正確處理方法可能因情況而異,並且如何處理特定錯誤的選擇是 留給較高級別函數(high_level_ABS)。