Як реалізувати обробку помилок [закрито]


13

Хоча я кілька років програмував на професійному рівні, я все ще не повністю розумію поводження з помилками. Хоча мої програми працюють чудово, поводження з помилками не реалізується на професійному рівні і є поєднанням і відповідності ряду методик.

За моєю обробкою помилок немає жодної структури. Я хотів би дізнатися і зрозуміти, як це реалізується на професійному рівні. Це одна сфера, де мені не вистачає знань.

Коли я повинен використовувати винятки і коли потрібно повернути статус успіху, щоб перевіритись у логічному потоці? Чи добре змішувати винятки та повертати статус?

Я в основному кодую в C #.


2
Чому голосування проти? Я задаю серйозне запитання щодо реалізації помилок та способів її виконання. Якщо це не найкраще місце, щоб задати таке питання програмістам, то де це? Мені насправді доводить помилок, коли люди голосують за такі питання, бо більше ніде не можна задавати таке питання. Це, можливо, єдине місце в Інтернеті, де я збираюся отримати надійну відповідь та можливі ресурси. Тож замість того, щоб голосувати за те, що інші люди, безумовно, Google, чи не було б простіше відповісти на це?
Джеймс Джефрі

6
Ваше запитання дуже широке. Можливо, ви могли б звузити сферу, пов’язавши конкретні приклади того, як вам не вдалося досягти своїх цілей кодування.
Andyz Smith

У Інтернеті є багато статей про поводження з помилками: Спробуйте: msdn.microsoft.com/en-us/library/seyhszts.aspx
Nir Kornfeld

Відповіді:


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

  2. Не використовуйте винятки для обробки неправильного коду. Щоб перевірити правильність коду, слід використовувати або твердження, або, у .NET Framework 4 і пізніших, контракти з кодом (які замінюють твердження і мають додаткові, особливо цінні функції).

  3. Не використовуйте винятки у виняткових випадках. Те, що користувач, коли його попросили ввести номер, ввів "собаку", не такий винятковий, щоб заслужити виняток.

  4. Будьте уважні, обираючи типи винятків. Створіть власні типи за потреби. Ретельно вибирали спадщину, маючи на увазі, що спіймані батьки захоплять і дітей. Ніколи throw Exception.

  5. Не використовуйте коди повернення для помилок. Коди помилок легко маскуються, ігноруються, забуваються. Якщо є помилка, або виправте її, або розповсюдьте її у верхній стек.

  6. У випадках, коли очікується, що метод поверне помилку і помилка не є винятковою, використовуйте переписки, ніколи не номери помилок. Приклад:

    // Note that the operation fails pretty often, since it deals with the servers which are
    // frequently unavailable, and the ones which send garbage instead of the actual data.
    private LoadOperationResult LoadProductsFromWeb()
    {
        ...
    }
    

    Значення LoadOperationResult.ServerUnavailable, LoadOperationResult.ParsingErrorі т. Д. Набагато чіткіше, ніж, скажімо, пам’ятати, що код 12 означає, що сервер не працює, а код 13 - що дані неможливо проаналізувати.

  7. Використовуйте коди помилок, коли вони посилаються на загальні, відомі кожному розробнику, який працює в певній галузі. Наприклад, не винаходити значення перерахунку для HTTP 404 Not Found або HTTP 500 Internal Server Error.

  8. Остерігайтеся буленів. Рано чи пізно вам захочеться дізнатися не лише про те, чи вдався чи не вдався конкретний метод, але й чому. Винятки та перерахунки набагато сильніші для цього.

  9. Не вловлюйте кожного винятку (якщо ви не знаходитесь у самій вершині стека). Якщо ви спіймаєте виняток, ви повинні бути готові впоратися з цим. Якщо все зробити, це означає, що вам все одно, чи правильно працює ваш код. Це може вирішити "Я не хочу шукати зараз, як це виправити", але рано чи пізно зашкодить вам.

  10. У C # ніколи не перезавантажуйте такі винятки:

    catch (SomeException ex)
    {
        ...
        throw ex;
    }
    

    бо ти ламаєш стек. Зробіть це замість цього:

    catch (SomeException)
    {
        ...
        throw;
    }
    
  11. Докладайте зусиль, коли пишете повідомлення про виключення. Скільки разів я бачив щось подібне throw Exception("wrong data")або throw Exception("shouldn't call this method in this context"). Інші розробники, включаючи себе через півроку, не мали б уявлення про те, що дані не так і чому ми не повинні називати якийсь метод у контексті, а також який саме.

  12. Не показуйте користувачеві повідомлення про виключення. Вони не очікуються від звичайних людей, а часто навіть не читаються для самих розробників.

  13. Не локалізуйте повідомлення про виключення. Пошук документації для локалізованого повідомлення є виснажливим та безглуздим: кожне повідомлення має бути лише англійською та англійською мовами.

  14. Не зосереджуйтесь виключно на винятках та помилках: журнали також надзвичайно важливі.

  15. У .NET, не забудьте включити винятки в документацію XML методу:

    /// <exception cref="MyException">Description of the exception</exception>

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

    У цьому сенсі¹, обробка виключень Java забезпечує суворіший та кращий підхід. Це змушує вас або мати справу з винятками, які потенційно можуть викликати названі методи, або заявити у своєму власному методі, що він може кидати винятки, з якими ви не працюєте, роблячи речі особливо прозорими.


¹ Враховуючи це, я вважаю різницю Java між винятками та помилками досить марною і заплутаною, враховуючи, що мова перевіряла вивірки та не перевіряла їх. На щастя, .NET Framework має лише винятки, і помилок немає.


Я навчився трохи цитувати з цього питання, чи можу я запитати, звідки цей список? Сайт чи особистий досвід? У будь-якому випадку виняткова робота (він отримає?).
Shelby115

@ Shelby115: список надходить із порядку: Обмін стеками, особистий досвід та Код, виконаний Стівом Макконелл.
Арсеній Муренко

Дякую @MainMa, що це чудова відповідь! Коли я був в університеті, я мав власність Code Complete, але хтось його вкрав. Я не зміг її прочитати.
Джеймс Джеффі

@JamesJeffery: тоді запозичіть друге видання у бібліотеці або придбайте одне: це одна з рідкісних книжок, що стосуються розвитку, яка цілком коштує грошей.
Арсеній Муренко

@MainMa Щойно замовив у Amazon, спасибі: DI також має чистий код, і зовсім забув про Главу 7.
Джеймс Джеффі

1

Я думаю, що список MainMa дуже повний. Я лише додам кілька своїх:

  1. Прочитайте статтю Еріка Ліпперта про те, як він класифікує винятки. Особливо важливим є його погляд на те, щоб не ловити винятки, які насправді є помилками у вашому коді. Виправити код замість цього!
  2. Якщо ви знаєте, що може статися виняток, і ви можете щось з цим зробити, впорайтеся з цим, але обмежте сферу дії, яку ви намагаєтеся наздогнати, і виберете конкретний виняток, якого ви очікуєте. Тобто, не робіть цього:

public void Foo() {
    try {
        //get input from use
        //do calculations
        //open file
    }
    catch (Exception ex) {
       //handle exception
    }
}

Замість цього робіть:

public void Foo() {
    //get input from use
    //do calculations
    try {
        //open file
    }
    catch (FileOpenException ex) {
       //handle exception
    }
}
  • Не використовуйте винятки для контролю потоку. Наприклад, не кидайте ClientNotFoundException у діалоговому вікні пошуку (клієнт, який не знайдений, не є винятковою у цій ситуації), і очікуйте, що код виклику покаже повідомлення "Не знайдено результатів", коли це станеться.

  • Не ковтайте винятки!

  • Майте на увазі, що справді обробка винятку може означати лише 3 речі:

    1. Повторіть операцію. Дійсно, лише якщо проблема є тимчасовою.
    2. Спробуйте альтернативу.
    3. Повідомте когось про проблему. Дійсний лише в тому випадку, якщо сповіщення діє, тобто користувач може щось зробити з цим.

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

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