Еквівалент "кидка" в R


140

Як можна "кинути" помилку в R? У мене є функція, яка приймає кадр даних та деякі назви стовпців і виконує їх роботи. Якщо стовпців не існує, я хочу, щоб функція зупинялася і зупиняла всі функції залежно від неї.

Я дивився recoverі browseта , tracebackале, а, здавалося, що вони близькі , але не те , що я шукаю.


2
Право, відновлення, веб-переглядач і прослідкування призначені для налагодження, тоді як системи пробування / лову - для обробки помилок у виробничому коді.
Харлан

20
Мені подобається, коли запитувачі запитують назву функції, яку вони шукають кілька разів у запитанні;)
hadley

Я думаю, що є причина, на яку це питання має більше результатів, ніж найкраща відповідь. Незважаючи на те, що це інше питання технічно не є темою, саме таким чудово викладеним підсумком незнайомої теми відомий Stack Overflow.
Йосія Йодер

Відповіді:


113

Дивіться help(tryCatch):

Умови сигналізуються символом " signalCondition". Крім того, функції
' stop' і ' warning' були змінені, щоб також приймати
аргументи умови.

та пізніше в розділі "Дивіться також":

' stop' і ' warning' умови сигналу, і ' try' по суті є спрощеною версією ' tryCatch'.

тому ти, мабуть, хочеш stop.


24
Це прекрасно працює. R настільки дивний, що їх не винна - він був розроблений задовго до того, як ми випрасували гарний інтерпретований дизайн мови.
forkandwait

5
На думку авторів, на неї сильно вплинула схема, яка є і старою, і хорошою. R - "пихатий", але з прикольними структурами даних. "Цікаві" частини R, ймовірно, пов'язані з тим, що багато конвенцій відрізняються від інших мов, зокрема сімейство мов C, що воно також синтаксично близьке. Я б здогадався, оскільки мова була розроблена купою статистиків, яким потрібен хороший інструмент, а не розробникам, які потребують хорошого інструменту. Тільки той факт, що "крапка" - це просто персонаж, зайняв багато часу.
KarlP

5
Деякі основні приклади тут були б чудовими, не лише цитатами. Тут stackoverflow.com/a/23917007/54964
Léo Léopold Hertz 준영

Я прийшов до цього питання, коли шукав, як повторно відкинути помилку в R із повідомленням про помилку збереження, але зберігаючи слід недоторканим (як у, ви виконуєте traceback()після помилки, щоб побачити, що пішло не так). Використання stopв errorаргументі tryCatchволі зіпсує слід. Однак finallyаргумент дозволить передати додаткове повідомлення та збереже корисність. Не зовсім тематично, але, я вважаю, достатньо важливим, щоб гарантувати кілька мінусів та загрозу поміркованості, що виштовхує цей коментар у вікно. :-)
Малі Реморкер


8

Поза базовими функціями, про які згадує Дірк:

У пакеті R.oo є додаткова функція обробки винятків, включаючи функцію кидання (), яка дуже корисна. Ви можете вилучити винятки за допомогою звичайних функцій спробувати або пробувати:

> try(throw("Division by zero.")); print("It's ok!");
Error: [2009-10-22 10:24:07] Exception: Division by zero.
[1] "It's ok!"

Більше про це можна прочитати тут: http://www1.maths.lth.se/help/R/R.oo/


8
Хе-хе. R не досить фанкі без ОО? Вибачте за фліп, і, безумовно, дякую за цікаву відповідь, але я піду із звичайною старою зупинкою () вище.
forkandwait

1
Зараз ще більше ОО. :)
Ітератор

3
@ws. Що таке дивного в R? plotграфік функції, try stop warnвся робота, як ви очікували, і майже все, що я хочу зробити, - це однолінійний.
ізоморфізм

4
Часто "потужність одноколірних" не є хорошою метрикою для мови. Для багатьох з нас, читабельний, зрозумілий, кодекс обробляє менше рядків. Дійсно, багато чого для мене не зрозуміле, тому що я початківець, і намагаюся відповідно відкалібрувати очікування. Але інші мови дозволяють досить інтуїтивно переходити від 0 до того, щоб виконувати завдання. R, здається, виробила культуру розумних, важких для читання однокласників. Я б заперечував за культуру максимально англійського коду, який часто також може бути однолінійним, як Рубі.
Філіп

6

Насправді ця функція stopifnotдуже зручна для здійснення перевірок правильності у вашому коді. Він приймає кілька логічних виразів і повертає помилку, якщо будь-який з них оцінює помилковий.

Приклад: Щоб перевірити, чи існує стовпець 'c' у фреймі даних 'df':

df <- data.frame(a = numeric(), b = numeric())
stopifnot(!is.null(df$c))

Це призведе до наступної помилки:

Error: !is.null(df$c) is not TRUE

Схоже, що Python's assert(...)...
Джосія Йодер

1

Ви можете перевірити, чи стовпець існує, і робити все, що завгодно.
Припустимо, data.frameназваний df1і перевірити, чи col1існує стовпець :

if(! any(grepl('^col1$',colnames(df1)))) stop("nonexistent column")

або

if(! any(grepl('^col1$',colnames(df1)))) return(-1)

Наприклад

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.