简体   繁体   English

R中如何结合tryCatch和If-Else语句?

[英]How to combine tryCatch and If-Else statements in R?

Aim目的

I have hundreds of Excel Workbooks.我有数百本 Excel 练习册。 There is a sheet in most of them, say, "Correct Sheet".其中大多数都有一张纸,比如“正确的纸”。 Those sheets should all have 10 columns.这些工作表都应该有 10 列。 I want to combine them all into one consolidated dataset (the Final Dataset).我想将它们全部组合成一个统一的数据集(最终数据集)。

However, some Workbooks do not have the Correct Sheet and when loading them, I get an error.但是,某些工作簿没有正确的工作表,加载它们时出现错误。 Where I do have Correct Sheets, some of them do not have 10 columns.我确实有正确的工作表,其中一些没有 10 列。 I want to exclude any Workbook that does not have a Correct Sheet or where the Correct Sheet does not have 10 columns.我想排除任何没有正确工作表或正确工作表没有 10 列的工作簿。

Attempt试图

Let's say that a correct sheet is a numerical variable.假设正确的工作表是一个数值变量。 Therefore, of the two variables below, only "b" is correct as it has a numerical value.因此,在下面的两个变量中,只有“b”是正确的,因为它具有数值。 a = "hello" b = 8 a = "你好" b = 8

Reprex代表

a <- "hello"
b <- 8


#A: Check that a + 2 does not produce an error
if(tryCatch({a + 2}, error = function(e) {"error"}) != "error") {
  
  #A1:If a+2 does not produce an error, then check that the sum is right
  if(a+2 == 10) {
    print("a No error and produced correct answer - Add 'a' to consolidated list")
  } else {
    
    #B: Check that b + 2 does not produce an error
    if(tryCatch({b+2}, error = function(e) {"error"}) != "error") {
      
      #B1:If b+2 does not produce an error, then check that the sum is right
      if(b+2 == 10) {
        print("a No error but produced wrong answer, 
              b No error and produced correct answer,
              Add 'b' to consolidated list")
      } else {
        print("a No error but produced wrong answer, b No error but produced wrong answer")
      }
      #B2: If b+2 produced an error
    } else {print("a No error but produced wrong answer, b Error")}
  }
  
  #A2:If a+2 produces an error, then go straight to b
} else {
    
    #B: Check that b + 2 does not produce an error
    if(tryCatch({b+2}, error = function(e) {"error"}) != "error") {
      
      #B1:If b+2 does not produce an error, then check that the sum is right
      if(b+2 == 10) {
        print("a Error, 
              b No error and produced correct answer, 
              Add 'b' to consolidated list")
      } else {
        print("a Error, b No error but produced wrong answer")
      }
      #B2: If b+2 produced an error
    } else {print("a Error, b Error")}
  }

Problem问题

I actually have three variables (eg a = "hello", b = 8, and c = "goodbye", which adds to the above complexity.我实际上有三个变量(例如 a =“你好”,b = 8 和 c =“再见”,这增加了上述复杂性。

Is there a simpler way of doing this?有更简单的方法吗?

You could try purrr::safely() .您可以尝试purrr::safely() Here's an analogue example using a nested list of “Excel workbooks”:下面是一个使用“Excel 工作簿”嵌套列表的模拟示例:

library(purrr)

# example "workbooks"
wkbks <- list(
  w1 = list(
    sheet1 = 1:3,
    `Correct Sheet` = 1:10
  ),
  w2 = list(
    sheet1 = 1:3
  ),
  w3 = list(
    `Correct Sheet` = 1:8
  ),
  w4 = list(
    `Correct Sheet` = 1:10,
    sheet2 = 1:5
  )
)

# helper function to read wkbk and throw error conditions not met
read_correct <- function(x) {
  stopifnot(length(x[["Correct Sheet"]]) == 10)
  x[["Correct Sheet"]]
}

# iterate over wkbks, wrapping `read_correct` in `safely()`
correct_sheets <- wkbks |>
  map(safely(read_correct)) |>
  transpose()

Results:结果:

# see all errors, removing NULLs
#> compact(correct_sheets$error)
$w2
<simpleError in .f(...): length(x[["Correct Sheet"]]) == 10 is not TRUE>

$w3
<simpleError in .f(...): length(x[["Correct Sheet"]]) == 10 is not TRUE>

# see all correct results, removing NULLs
#> compact(correct_sheets$result)
$w1
 [1]  1  2  3  4  5  6  7  8  9 10

$w4
 [1]  1  2  3  4  5  6  7  8  9 10

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM