У меня есть простой BackgroundWorker, который использует замыкания для своих обработчиков событий DoWork и RunWorkerCompleted, которые устанавливают и проверяют логическое значение соответственно. В упрощенном виде код (C # в .NET 3.5) выглядит следующим образом:
public void SomeMethod()
{
BackgroundWorker worker = new BackgroundWorker();
bool result = false;
worker.DoWork += new DoWorkEventHandler(
(sender, e) =>
{
result = LengthyOperation();
});
worker.RunWorkerCompleted +=new RunWorkerCompletedEventHandler(
(sender, e) =>
{
AppendRunLog("Result: " + (result ? "PASS" : "FAIL"));
});
worker.RunWorkerAsync();
}
SomeMethod вызывается из обработчика кнопок WPF в главном потоке пользовательского интерфейса.
Обычно это работает просто отлично, но время от времени я получаю отчет о том, что операция завершилась неудачно, когда должна была пройти (согласно журналам, сгенерированным внутри LengthyOperation), т.е. логический результат записывается как ложный в обработчике Completed, когда операция должна была вернуть true в обработчике DoWork.
Я проверил и протестировал код внутри LengthyOperation, чтобы убедиться, что в нем нет какой-то тонкой ошибки, и я уверен, что он чистый. Я не смог воспроизвести его в своей среде разработки.
Есть ли у меня состояние гонки при настройке и считывании значения результата? Я ожидаю, что операция присваивания будет завершена в DoWork до того, как будет запущено событие Completed.