AFM*_*AFM 12 c# multithreading async-await
我最近遇到了一个为async/await调用限制线程的例子.在我的机器上分析和播放代码后,我想出了一个稍微不同的做同样事情的方法.我不确定的是,发动机罩下发生的事情几乎是一样的,或者是否有任何微妙的差异需要注意?
这是基于原始示例的代码:
private readonly SemaphoreSlim _semaphore = new SemaphoreSlim(5);
public async Task CallThrottledTasks()
{
var tasks = new List<Task>();
for (int count = 1; count <= 20; count++)
{
await _semaphore.WaitAsync();
tasks.Add(Task.Run(async () =>
{
try
{
int result = await LongRunningTask();
Debug.Print(result.ToString());
}
finally
{
_semaphore.Release();
}
}));
}
await Task.WhenAll(tasks);
Debug.Print("Finished CallThrottledTasks");
}
Run Code Online (Sandbox Code Playgroud)
这是我对相同代码的看法:
private readonly SemaphoreSlim _semaphore = new SemaphoreSlim(5);
public async Task CallThrottledTasks()
{
var tasks = new List<Task>();
for (int count = 1; count <= 20; count++)
{
await _semaphore.WaitAsync();
tasks.Add(LongRunningTask().ContinueWith(t =>
{
try
{
int result = t.Result;
Debug.Print(result.ToString());
}
finally
{
_semaphore.Release();
}
}));
}
await Task.WhenAll(tasks);
Debug.Print("Finished CallThrottledTasks");
}
Run Code Online (Sandbox Code Playgroud)
我可能会离开,但似乎Task.Run方法正在创建一个运行LongRunningTask()的任务,然后添加一个继续来打印结果,而我的方法绕过Task.Run创建的任务并且有点精简结果是.这是准确的还是我离开基地?
Ste*_*ary 13
它不是很精简,只是一点点.通常,我避免ContinueWith使用async代码,因为await它更清晰,并且具有更async友好的默认语义.首先优化开发人员时间,然后针对其他考虑因素进行优化.
您的代码确实稍微改变了语义:在原始代码中,LongRunningTask是从线程池上下文执行的,而在您的代码中,它是从CallThrottledTasks上下文执行的.此外,您的代码不会LongRunningTask干净地传播异常; Task<T>.Result将包装异常AggregateException,而await不会进行任何包装.
| 归档时间: |
|
| 查看次数: |
9057 次 |
| 最近记录: |