Правильно ли я игнорировать предупреждение компилятора из-за отсутствия ожидания этого асинхронного вызова?

У меня есть следующий метод, который запускается, когда исключение возникает в части моего приложения Metro

void Model_ExceptionOccured(Exception ex)
{
    var dlg = new Windows.UI.Popups.MessageDialog("An exception occured during verification: " + ex.Message, "Exception");
    dlg.ShowAsync();
}

"dlg.ShowAsync()" - вызов асинхронный, но я не хочу ждать результата. Компилятор генерирует для него предупреждение:

Because this call is not awaited, execution of the current method continues before the call is completed. Consider applying the 'await' operator to the result of the call.

Мне все равно? Есть ли причина, по которой я должен добавить ключевое слово ожидания, кроме как избавиться от предупреждения?

Ответ 1

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

http://msdn.microsoft.com/en-us/library/hh965065(v=vs.110).aspx (VB.NET)

http://msdn.microsoft.com/en-us/library/hh873131.aspx (С#)

Ответ 2

Проблема в том, что если код в dlg.ShowAsync(); выдает исключение, он будет оставлен необработанным и будет повторно выведен позже потоком Finalizer, потенциально вызывающим завершение вашей программы.

Что происходит в действительности, зависит от политики .NET исключений

В этой статье в MSDN упоминается следующее:

Если вы не ждете от задачи, которая распространяет исключение, или доступа к свойству Exception, исключение перераспределяется в соответствии с политикой исключения .NET, когда задача собирает мусор.

Когда VS 2012 был отправлен, политика по умолчанию для необработанных исключений задач изменилась с процесса завершения, чтобы игнорировать исключение.

Ответ 3

Я столкнулся с той же проблемой, и вот мое решение:

Я создал объект Task, назначил вывод функции async объекту Task и использовал таймер для периодической проверки состояния задачи.

Вот краткий пример: (в обработчике события Update_Click)

StatusLabel.Text = "Preparing " + feedArticleList1.Feed.Title;
UpdateCheck.Enabled = true;
UpdateTask = feedArticleList1.Feed.UpdateFeedAsync();

Позже, в обработчике событий для моего таймера, я проверяю UpdateTask.Status:

switch (UpdateTask.Status)
{
    case TaskStatus.Canceled:
    case TaskStatus.Created:
    case TaskStatus.Running:
    case TaskStatus.WaitingForActivation:
    case TaskStatus.WaitingForChildrenToComplete:
    case TaskStatus.WaitingToRun:
        StatusLabel.Text = UpdateTask.Status.ToString();
        break;
    case TaskStatus.RanToCompletion:
        StatusLabel.Text = "Update Complete " + DateTime.Now.ToShortTimeString();
        UpdateCheck.Enabled = false;
        break;
    case TaskStatus.Faulted:
        throw (UpdateTask.Exception);
    default:
        break;
}