我知道Task.Wait()
会阻塞它所在的线程。
那么,我是否正确理解Task.WaitAsync()
不会这样做?
我试图找到相关信息,但没有找到任何内容。
我知道Task.Wait()
会阻塞它所在的线程。
那么,我是否正确理解Task.WaitAsync()
不会这样做?
我试图找到相关信息,但没有找到任何内容。
WaitAsync 将返回一个新的需要依次等待的任务。它不是用来避免await
,而是用于允许取消等待另一个任务。
如果你想要等待一个任务完成而不阻塞,你将需要在一个async
方法中使用await
,或者使用ContinueWith
与继续代码:
async Task MyMethodAsync(Task myTask)
{
...
await myTask;
...
}
Task.WaitAsync
。...
try
{
await myTask.WaitAsync(TimeSpan.FromMinute(1));
}
catch(TimeoutException)
{
//Handle the timeout
}
...
或者,如果父调用通过 CancellationTokenSource
发出取消信号,您可能希望取消等待该任务。
async Task MyMethod(Task someTask,CancellationToken cancellationToken=default)
{
....
await someTask.WaitAsync(cancellationToken);
...
}
它是非阻塞的,因为它返回一个Task
。请查看文档。
public Task WaitAsync(CancellationToken cancellationToken);
public Task WaitAsync(TimeSpan timeout);
public Task WaitAsync(TimeSpan timeout, CancellationToken cancellationToken);
获取一个
Task
,该任务将在此Task
完成、指定的超时时间到期或指定的CancellationToken
请求取消时完成。
实现可在此处找到:
public static Task WaitAsync(this Task task, int millisecondsTimeout) =>
WaitAsync(task, TimeSpan.FromMilliseconds(millisecondsTimeout), default);
public static Task WaitAsync(this Task task, TimeSpan timeout) =>
WaitAsync(task, timeout, default);
public static Task WaitAsync(this Task task, CancellationToken cancellationToken) =>
WaitAsync(task, Timeout.InfiniteTimeSpan, cancellationToken);
public async static Task WaitAsync(this Task task, TimeSpan timeout, CancellationToken cancellationToken)
{
var tcs = new TaskCompletionSource<bool>();
using (new Timer(s => ((TaskCompletionSource<bool>)s).TrySetException(new TimeoutException()), tcs, timeout, Timeout.InfiniteTimeSpan))
using (cancellationToken.Register(s => ((TaskCompletionSource<bool>)s).TrySetCanceled(), tcs))
{
await(await Task.WhenAny(task, tcs.Task).ConfigureAwait(false)).ConfigureAwait(false);
}
}
Task.WaitAsync()
在你想要根据超时时间来取消Task
并且不阻塞执行时非常有用。 - undefined