2015-03-08 1 views
1

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

BackgroundWorker backgroundWorker = new BackgroundWorker(); 
backgroundWorker.DoWork += delegate 
{ 
    //code 
}; 
backgroundWorker.RunWorkerAsync(); 
while (backgroundWorker.IsBusy) 
{ 
    Application.DoEvents(); 
} 

Просто хочу знать, если есть способ, чтобы упростить этот код, так что я не эффективно дублировать один и тот же блок кода для всех моих кнопок.

EDIT: Типичный код, который я пытаюсь запустить вдоль линий:

//Synchronous task 
Wait(2000); 
//Synchronous task 
return taskResult ? "Success" : "Failure" 
+3

У вас есть знакомства с async и ждут? Вы можете с легкостью добавить код обработчика в асинхронные методы. – Crowcoder

+0

Нет настоящего знакомства с ним, но я прочитал его для NET 4.5. Просто не нашли времени, чтобы узнать об этом. Любые преимущества для этого? –

+3

Вы своего рода поражение цели фонового работника, зацикливаясь на событиях. – Les

ответ

4

Без больше контекста, это невозможно предложить очень конкретные улучшения. Тем не менее, вы наверняка избавитесь от цикла while. Просто используйте:

BackgroundWorker backgroundWorker = new BackgroundWorker(); 
backgroundWorker.DoWork += delegate 
{ 
    //code 
}; 
backgroundWorker.RunWorkerAsync(); 

Обратите внимание, что если у вас есть код, который вы хотите выполнить, когда BackgroundWorker задача завершается (возможное объяснение того, почему у вас что while цикл в первую очередь), что-то, как это будет работать (вместо с помощью петли while вы имели прежде):

BackgroundWorker backgroundWorker = new BackgroundWorker(); 
backgroundWorker.DoWork += delegate 
{ 
    //code 
}; 
backgroundWorker.RunWorkerCompleted += (sender, e) => 
{ 
    // code to execute when background task is done 
}; 
backgroundWorker.RunWorkerAsync(); 

в современном C#, BackgroundWorker почти устарели. Основным преимуществом, которое он предоставляет сейчас, является удобная отчетность о проделанной работе, и на самом деле ее легко получить, используя Progress<T>.

Если вам не нужно сообщать о прогрессе, факторинг код, чтобы использовать async/await легко:

await Task.Run(() => 
{ 
    //code 
}); 

// code to execute when background task is done 

Если вам не нужно сообщать о прогрессе, это лишь немного сложнее:

Progress<int> progress = new Progress<int>(); 

progress.ProgressChanged += (sender, progressValue) => 
{ 
    // do something with "progressValue" here 
}; 

await Task.Run(() => 
{ 
    //code 

    // When reporting progress ("progressValue" is some hypothetical 
    // variable containing the progress value to report...Progress<T> 
    // is generic so you can customize to do whatever you want) 
    progress.Report(progressValue); 
}); 

// code to execute when background task is done 

Наконец, в некоторых случаях вам может понадобиться задача вернуть значение. В этом случае это выглядело бы так:

var result = await Task.Run(() => 
{ 
    //code 

    // "someValue" would be a variable or expression having the value you 
    // want to return. It can be of any type. 
    return someValue; 
}); 

// At this point in execution "result" now has the value returned by the 
// background task. Note that in the above example, the method itself 
// is anonymous and so you could just set a local variable at the end of the 
// task; the value-returning syntax is more useful when you are calling an 
// actual method that itself returns a value, and is especially useful when 
// you are calling an `async` method that returns a value (i.e. you're not 
// even using `Task.Run()` in the `await` statement. 

// code to execute when background task is done 

Вы можете смешивать и сопоставлять вышеуказанные методы при необходимости.

+0

Спасибо за это.На самом деле я не мог понять, как мне нужно было анонсировать мой код с помощью async. –

+0

Одна вещь, которую я до сих пор не понимаю, - это то, почему вам не нужно асинхронно до «() =>». Из моего ограниченного понимания я подумал, что вам нужно использовать ключевое слово async, чтобы затем использовать ключевое слово ожидания. Также я прав, говоря, что я мог бы использовать Task.Wait() вместо ожидания? или это не достигает того же результата. –

+0

@MayuraVivekananda: «почему вам не нужна асинхронность перед«() => '»- анонимный метод (объявленный с использованием этого синтаксиса лямбда) сам не вызывает' await', поэтому ему не нужно 'async '. Вся задача, представленная этим анонимным методом, выполняется асинхронно, обертывая ее при вызове 'Task.Run()', но сам метод запускается целиком в единственной «Задаче», созданной методом «Run()» , –

 Смежные вопросы

  • Нет связанных вопросов^_^