C# 为异步函数实现WaitAsync方法

C# 为异步函数实现WaitAsync方法

​.NET 6 开始,System.Threading.Tasks.Task类 ​原生提供了 WaitAsync方法,该方法可以很方便的为任意异步函数提供超时功能。但是Framework没有该方法。不过我们可以通过Task.WhenAny方法可以实现类似的功能 。

  1. 无返回值
csharp 复制代码
/// <summary>
/// 异步等待任务完成,支持超时
/// </summary>
/// <param name="task">要等待的任务</param>
/// <param name="timeoutMilliseconds">超时时间(毫秒)</param>
/// <returns>任务本身</returns>       
public static async Task WaitAsync(this Task task, int timeout)
{
    if (task == null)
        throw new ArgumentNullException(nameof(task));
    if (task.IsCompleted)
        return;
    using (CancellationTokenSource cts = new CancellationTokenSource())
    {
        Task completedTask = await Task.WhenAny(task, Task.Delay(timeout, cts.Token)).ConfigureAwait(false);
        if (completedTask != task)
            throw new TimeoutException($"等待任务超时({timeout} 毫秒)");
        cts.Cancel();
        await task.ConfigureAwait(false);
    }
}
  1. 有返回值
csharp 复制代码
/// <summary>
/// 异步等待一个 Task<T> 完成,并获取结果,支持超时
/// </summary>
/// <typeparam name="T">任务返回的数据类型</typeparam>
/// <param name="task">要等待的任务</param>
/// <param name="timeoutMilliseconds">超时时间(毫秒)</param>
/// <returns>任务的结果 T</returns>      
public static async Task<T> WaitAsync<T>(this Task<T> task, int timeout)
{
    if (task == null)
        throw new ArgumentNullException(nameof(task));
    if (task.IsCompleted)
        return task.Result;
    using (CancellationTokenSource cts = new CancellationTokenSource())
    {
        Task completedTask = await Task.WhenAny(task, Task.Delay(timeout, cts.Token)).ConfigureAwait(false);
        if (completedTask != task)
            throw new TimeoutException($"等待任务超时({timeout} 毫秒)");
        cts.Cancel();
        return await task.ConfigureAwait(false);
    }
}
相关推荐
❀͜͡傀儡师2 小时前
快速定位并解决Java应用CPU占用过高问题
java·开发语言·python
冬天vs不冷2 小时前
Java基础(十五):注解(Annotation)详解
android·java·python
逆风优雅2 小时前
vue 实现自定义message 全局提示
前端·javascript·vue.js
唐青枫2 小时前
C#.NET MemoryCache 深入解析:本地缓存机制与最佳实践
c#·.net
艾小码2 小时前
前端开发者必看!JavaScript这些坑我替你踩过了
前端·javascript
浮游本尊2 小时前
React 18.x 学习计划 - 第六天:React路由和导航
前端·学习·react.js
元亓亓亓3 小时前
Leet热题100--208. 实现 Trie (前缀树)--中等
java·开发语言
拾荒的小海螺3 小时前
C#:OpenCvSharp 实现图像处理的技术指南
开发语言·图像处理·c#
拿破轮3 小时前
不小心在idea中点了add 到版本控制 怎么样恢复?
java·ide·intellij-idea