我是一个 TPL 新手。不确定这个库是否是要走的路,但我想按顺序运行一组异步任务,但不阻塞 UI,而是按顺序运行并按启动顺序回调 - 有点像运行它们同步。因此,只有在任务完成并有 HttpResponseMessage 时才会有效地回调。然后才开始下一个任务。
所以行为将是
运行长时间运行的任务 1,当它完成回调时,我们可以对 UI 做一些事情,然后运行下一个长时间运行的任务,当它完成回调时,我们可以更新 UI。运行一个较短的任务,当它完成回调以便我们可以更新 UI
我已经看到了一些使用调度程序的示例,但无论如何这是我的代码
private void RunSequentially()
{
var lcts = new LimitedConcurrencyLevelTaskScheduler(1);
var factory = new TaskFactory(lcts);
string username = "user";
string password = "password";
var handler = new HttpClientHandler
{
Credentials = new NetworkCredential(username, password), PreAuthenticate = true
};
var client = new HttpClient(handler);
List<Tuple<string,string,string>> taskTuples = new List<Tuple<string, string, string>>();
taskTuples.Add(new Tuple<string, string, string>("POST", "http://longrunning", XDocument.Load(@"./somefile.xml").ToString()));
taskTuples.Add(new Tuple<string, string, string>("GET", "http://getItem", null));
factory.StartNew(
() =>
{
foreach(var tuple in taskTuples)
{
ProcessSequentially(tuple,ProcessCallback, client);
}
});
}
和 ProcessSequentially 方法
private async void ProcessSequentially(Tuple<string, string, string> tuple, Action<string> callback, HttpClient client)
{
HttpResponseMessage message = null;
if (tuple.Item1 == "POST")
{
message = await
client.PostAsync(
tuple.Item2,
new StringContent(tuple.Item3));
}
else
{
message = await
client.GetAsync(
tuple.Item2);
}
callback(message.ReasonPhrase);
}
现在假设 post 任务将是长时间运行的任务 - 我需要先启动长时间运行的任务并首先回调,然后在第一个回调后启动短时间运行的 GET,而不必通过 WaitAll 阻塞 UI等有没有办法做到这一点,也许作为 TPL 或 TPL 数据流中的一个事务,因为在我运行这个的那一刻,POST 确实首先开始,但是因为 get 是一个快速操作,它首先完成并首先返回,我想它们像同步操作一样按顺序发生...
因此,为了更改代码 - 这会是更好的方法吗?
foreach (var tuple in taskTuples)
{
factory.StartNew(
() =>
{
this.ProcessSequentially(tuple,client);
}).ContinueWith(this.FinishSequentialTask);
}