Menu
Coddy logo textTech

Przechwytywanie błędów za pomocą tryCatch()

Część sekcji Logika i przepływ sterowania ścieżki R w Coddy. Lekcja 53 z 64.

tryCatch(expr, error = function(e) ...) uruchamia expr. Jeśli wystąpi błąd, zamiast niego uruchamiana jest procedura obsługi, a jej wartość staje się wynikiem; skrypt działa dalej:

safe_sqrt <- function(x) {
  tryCatch(sqrt(x), error = function(e) NA)
}
print(safe_sqrt(16))
print(safe_sqrt("a"))
print("still running")

Wynik:

[1] 4
[1] NA
[1] "still running"

Procedura obsługi otrzymuje błąd jako e, a conditionMessage(e) zwraca jego treść:

result <- tryCatch(
  stop("file not found"),
  error = function(e) paste("Problem:", conditionMessage(e))
)
print(result)

Wynik:

[1] "Problem: file not found"

Opakuj tylko wywołanie, które może się nie powieść, i obsłuż błąd tam, gdzie możesz zrobić coś użytecznego, na przykład zwrócić wartość domyślną lub wyświetlić komunikat użytkownikowi:

to_number <- function(s) {
  tryCatch({
    if (s == "") stop("empty input")
    as.integer(s)
  }, error = function(e) -1L)
}
print(to_number("42"))
print(to_number(""))

Wynik:

[1] 42
[1] -1

W pętli tryCatch() pozwala, aby jeden nieprawidłowy element spowodował błąd, podczas gdy pozostałe są nadal przetwarzane:

inputs <- list(4, "x", 9)
for (v in inputs) {
  r <- tryCatch(sqrt(v), error = function(e) "not a number")
  cat(format(v), "->", r, "\n")
}

Wynik:

4 -> 2 
x -> not a number 
9 -> 3 
challenge icon

Wyzwanie

Łatwy

Uzupełnij safe_divide(a, b). Użyj tryCatch(): wewnątrz zgłoś błąd division by zero, gdy b wynosi 0, a w przeciwnym razie oblicz a / b. Obsługa błędu zwraca Error: , po którym następuje komunikat. Zwróć wynik zaokrąglony do dwóch miejsc po przecinku jako tekst, 3.33, albo tekst błędu.

Dostarczony kod odczytuje pary liczb, takie jak 10/3, oddzielone przecinkami, i wypisuje wynik każdej pary w osobnym wierszu.

Spróbuj swoich sił

safe_divide <- function(a, b) {
  # Wpisz tutaj swój kod
  ""
}

# Dostarczony kod wejścia/wyjścia: pozostaw go bez zmian
input <- suppressWarnings(readLines(file("stdin")))
for (pair in strsplit(input[1], ",")[[1]]) {
  p <- as.numeric(strsplit(pair, "/")[[1]])
  cat(safe_divide(p[1], p[2]), "\n", sep = "")
}
quiz iconSprawdź się

Ta lekcja zawiera krótki quiz. Zacznij lekcję, żeby na niego odpowiedzieć i śledzić swoje postępy.

Wszystkie lekcje w sekcji Logika i przepływ sterowania

Poćwicz samodzielnie: Kompilator R online