在我的應用程序中,我需要在某些設定的時間間隔內連續處理Work
的部分作品。我原本寫了一個Task
來持續檢查給定的Task.Delay
以查看它是否完成,如果是這樣的話Work
將被處理,對應於Task.Delay
。這種方法的缺點是Task
,當沒有Task.Delay
完成時,檢查這些Task.Delays
將處於假無限循環。應該/可以將這個「遞歸任務」表示爲任務連續?
爲了解決這個問題,我發現我可以根據需要創建一個「遞歸Task
」(我不確定這是什麼術語)以給定間隔處理工作。
// New Recurring Work can be added by simply creating
// the Task below and adding an entry into this Dictionary.
// Recurring Work can be removed/stopped by looking
// it up in this Dictionary and calling its CTS.Cancel method.
private readonly object _LockRecurWork = new object();
private Dictionary<Work, Tuple<Task, CancellationTokenSource> RecurringWork { get; set; }
...
private Task CreateRecurringWorkTask(Work workToDo, CancellationTokenSource taskTokenSource)
{
return Task.Run(async() =>
{
// Do the Work, then wait the prescribed amount of time before doing it again
DoWork(workToDo);
await Task.Delay(workToDo.RecurRate, taskTokenSource.Token);
// If this Work's CancellationTokenSource is not
// cancelled then "schedule" the next Work execution
if (!taskTokenSource.IsCancellationRequested)
{
lock(_LockRecurWork)
{
RecurringWork[workToDo] = new Tuple<Task, CancellationTokenSource>
(CreateRecurringWorkTask(workToDo, taskTokenSource), taskTokenSource);
}
}
}, taskTokenSource.Token);
}
如果/可這是與Task.ContinueWith
鏈表示?這樣的實現會有什麼好處嗎?目前的實施有什麼重大錯誤嗎?
您應該使用'ConcurrentDictionary'。 – SLaks
你的「循環任務」只是一個循環中效率較低的版本「await」。 (但首先不要這樣做) – SLaks
@KDecker:不,你應該使用'await'而不是'ContinueWith'。 –