Как отличить разные типы исключений в обработчике событий BackgroundWorker.RunWorkerCompleted - PullRequest
4 голосов
/ 07 октября 2010

Я занимаюсь небольшим хобби-проектом на C #, языке, которого я плохо знаю, и наткнулся на следующее:

Предположим, у вас есть асинхронная операция, реализованная с помощью BackgroundWorker.Теперь, если есть исключение, событие RunWorkerCompleted будет вызвано, и RunWorkerCompletedEventArgs.Error будет не нулевым.

Является ли следующий канонический способ обработки различных типов исключений?(Здесь все виды исключений - наследование WRT братьев и сестер)

if (e.Error != null)
{
    FirstKindOfException e1 = e as OneKindOfException;
    SecondKindOfException e2 = e as SecondKindOfException;
    ...
    LastKindOfException en = e as LastKindOfException;
    if (e1 != null)
    {
        ...
    }
    else if (e2 != null)
    {
        ...
    }
    ...
    else
    {
        ...
    }
}

Работает, но ... не чувствует правильно .

Ответы [ 4 ]

7 голосов
/ 07 октября 2010

Вы можете использовать is, чтобы держать каждый тест в узком диапазоне:

if (e.Error is FirstKindOfException )
{
    ...
}
else if (e.Error is SecondKindOfException)
{
    ...
}

(затем повторите приведение, если вы хотите получить специальные значения из исключения)

Честно говоря, довольно редко мне приходится обрабатывать лотов различных типов исключений. В большинстве случаев можно просто восстановить (компенсировать) известное состояние и сообщить об ошибке соответствующим образом. Обычно я предпочитаю проверять возможные ошибки до Я начинаю действие, поэтому исключение действительно является чем-то исключительным

5 голосов
/ 07 октября 2010

Используйте оператор is :

if (e.Error is FirstKindOfException) {
   //...
}
else if (e.Error is SecondKindOfException) {
   //...
}
//etc..

Или просто прервите его, так как вы все равно не знаете, как обрабатывать эти исключения. Если бы вы это сделали, вы бы поймали их в обработчике событий DoWork (), нет смысла пытаться обработать их после того, как состояние испарится:

if (e.Error != null) throw new BackgroundTaskFailedException(e.Error);
2 голосов
/ 07 октября 2010

Использование оператора is возможно?

if (e is OneKindOfException)
{
}
else if (e is SecondKindOfException)
{
}
1 голос
/ 07 октября 2010

Да, вы можете сделать это, но действительно зависит от того, что вы собираетесь делать со всеми этими типами исключений.Обычно это будет показано только пользователю, поэтому нет необходимости проверять тип ошибки.

Также необходимо помнить, что вполне вероятно, что тип исключения может быть AggregateException - это результат операций Task<T> - поэтому вам нужно быть осторожным.

...