我有一個利用TPL的C#WinForms(.NET 4.5.2)應用程序。該工具具有同步功能,該功能被傳遞到任務工廠X
次數(具有不同的輸入參數),其中X
是在開始該過程之前用戶聲明的數字。任務開始並存儲在List<Task>
中。C#在任何給定時間運行X個任務<T>,同時保持WinForm響應
假設用戶輸入5
,我們有這個在async
按鈕單擊處理程序:
for (int i = 0; i < X; i++)
{
var progress = Progress(); // returns a new IProgress<T>
var task = Task<int>.Factory.StartNew(() => MyFunction(progress), TaskCreationOptions.LongRunning);
TaskList.Add(task);
}
每個progress
實例更新UI。
現在,只要一個任務完成,我想要啓動一個新的。從本質上講,這個過程應該無限期地運行,任何時候都有X
任務運行,除非用戶通過UI取消(我將使用取消令牌)。我嘗試使用以下方法來實現此目的:
while (TaskList.Count > 0)
{
var completed = await Task.WhenAny(TaskList.ToArray());
if (completed.Exception == null)
{
// report success
}
else
{
// flatten AggregateException, print out, etc
}
// update some labels/textboxes in the UI, and then:
TaskList.Remove(completed);
var task = Task<int>.Factory.StartNew(() => MyFunction(progress), TaskCreationOptions.LongRunning);
TaskList.Add(task);
}
這是陷入用戶界面。有沒有更好的方法來實現這個功能,同時保持UI的響應?
有人建議在使用TPL數據流提出的意見,但由於時間的限制和規範,替代解決方案,歡迎
更新
我不知道進展情況報告是否可能是問題?這裏是什麼樣子:
private IProgress<string> Progress()
{
return new Progress<string>(msg =>
{
txtMsg.AppendText(msg);
});
}
是否有任何理由不使用專門的工具來完成此任務?您的場景正是TPL Dataflow所設計的。 –
是的,我第二次基里爾 - TPL Dataflow聽起來很適合這個。 –
時間限制,項目規格,並沒有意識到數據流(將有一個閱讀,並無論如何,建議,謝謝) – globetrotter