System.Threading.Tasks.Extensions介绍

发布时间 2023-09-06 17:10:22作者: 非法关键字

System.Threading.Tasks.Extensions 是一个用于扩展 .NET 中任务(Task)的库,它提供了一些额外的功能,特别是在异步编程方面。这个库引入了一些新的方法和功能,包括:

  1. ConfigureAwait:它引入了 ConfigureAwait 方法,允许你在任务之间配置不同的上下文(例如,同步上下文或异步上下文),以便更好地控制异步代码的执行上下文。
  2. IterateIterate 方法允许你在异步迭代中使用 await,从而使异步循环更加容易和直观。
  3. ValueTask:引入了 ValueTask<T> 结构,这是一种轻量级的值类型,用于表示一个可能是同步也可能是异步的操作的结果。这可以提高性能,减少异步操作的开销。
  4. AsyncIteratorAsyncIterator<T> 类型是一个可枚举异步序列的实现,它使你可以使用 await foreach 循环异步枚举序列。
  5. WithCancellationWithCancellation 方法允许你为任务添加取消令牌,以便在取消操作时终止任务。
  6. WaitAsyncWaitAsync 方法是 Task.WhenAny 的扩展方法,它使你可以等待多个任务中的任何一个完成,并返回完成的任务。

这些功能扩展了 .NET 中异步编程的能力,使开发人员能够更方便地编写高效的异步代码。如果你在使用异步任务时遇到特定的需求或问题,System.Threading.Tasks.Extensions 可能会提供一些有用的工具和方法。

WithCancellation 方法的主要用途是在异步任务中添加取消支持。这在以下情况下非常有用:

  1. 长时间运行的操作:当你有一个可能需要较长时间才能完成的异步操作时,你可以使用 WithCancellation 来允许用户或系统取消该操作,而不必等待其完成。
  2. 用户交互:在用户界面(如 WPF 或 WinForms)中,用户可能会要求取消某些操作。你可以使用 WithCancellation 来允许用户在操作进行时取消它们。
  3. 资源释放:在某些情况下,你可能需要确保异步操作在取消时释放相关资源。WithCancellation 可以帮助你在取消时执行清理工作。

当需要执行一个长时间运行的异步操作,并且希望支持取消操作,但同时也要执行一些不需要取消支持的子操作时,你可以使用 WithCancellation 来实现这一目标。以下是一个示例,结合了 WithCancellation 的使用,其中包含了长时间运行的文件下载操作:

using System;
using System.IO;
using System.Net.Http;
using System.Threading;
using System.Threading.Tasks;

class Program
{
    static async Task Main(string[] args)
    {
        using var cts = new CancellationTokenSource();

        // 创建一个取消令牌,用于取消整个操作
        var cancellationToken = cts.Token;

        var downloadTask = DownloadFileAsync("https://example.com/somefile.txt", cancellationToken);

        // 等待用户输入以取消整个操作
        Console.WriteLine("Press Enter to cancel the operation...");
        Console.ReadLine();

        // 发出取消请求
        cts.Cancel();

        try
        {
            await downloadTask;
            Console.WriteLine("File downloaded successfully.");
        }
        catch (OperationCanceledException)
        {
            Console.WriteLine("Operation was canceled.");
        }
        catch (Exception ex)
        {
            Console.WriteLine($"An error occurred: {ex.Message}");
        }
    }

    static async Task DownloadFileAsync(string url, CancellationToken cancellationToken)
    {
        using var httpClient = new HttpClient();

        // 使用WithCancellation包装异步操作,以便支持取消
        var response = await httpClient.GetAsync(url).WithCancellation(cancellationToken);

        if (response.IsSuccessStatusCode)
        {
            // 从响应中读取内容,并处理文件下载
            var contentStream = await response.Content.ReadAsStreamAsync();
            using var fileStream = File.Create("downloadedFile.txt");
            await contentStream.CopyToAsync(fileStream);
        }
        else
        {
            throw new InvalidOperationException($"Failed to download file. Status code: {response.StatusCode}");
        }
    }
}

在这个示例中,我们创建了一个 DownloadFileAsync 方法,该方法使用 WithCancellation 包装了 HttpClient 异步操作,以支持取消。同时,我们也创建了一个取消令牌 cancellationToken,以便在用户要求取消操作时终止整个操作。如果用户取消了操作,将捕获 OperationCanceledException,否则,我们会在文件下载完成时正常输出成功信息。这个示例结合了长时间运行的文件下载和取消操作的需求。