当前位置:  开发笔记 > 编程语言 > 正文

如何等待IAsyncEnumerable <>的所有结果?

如何解决《如何等待IAsyncEnumerable<>的所有结果?》经验,为你挑选了1个好方法。

我正在修补IAsyncEnumerableC#8.0中的新内容。假设我有一些我想使用的方法:

public IAsyncEnumerable SomeBlackBoxFunctionAsync(...) { ... }

我知道我可以将其与await foreach...语法一起使用。但是,可以说,我的使用者需要从该功能中获得所有结果,然后才能继续。在继续之前等待所有结果的最佳语法是什么?换句话说,我希望能够执行以下操作:

// but that extension - AllResultsAsync() - doesn't exist :-/
List myList = await SomeBlackBoxFunctionAsync().AllResultsAsync(); 

正确的方法是什么?



1> Panagiotis K..:

首先发出警告:按照定义,异步流可​​能永远不会结束,并且会继续产生结果,直到应用程序终止。这已经在SignalR或gRPC中使用。轮询循环也以这种方式工作。

使用ToListAsync上的异步流可能产生意想不到的后果。


这样的操作员已经可以通过System.Linq.Async包获得。

通过ToListAsync可以使用整个流。该代码*看似简单,但隐藏了一些有趣的问题:

public static ValueTask> ToListAsync(this IAsyncEnumerable source, CancellationToken cancellationToken = default)
{
    if (source == null)
        throw Error.ArgumentNull(nameof(source));

    if (source is IAsyncIListProvider listProvider)
        return listProvider.ToListAsync(cancellationToken);

    return Core(source, cancellationToken);

    static async ValueTask> Core(IAsyncEnumerable source, CancellationToken cancellationToken)
    {
        var list = new List();

        await foreach (var item in source.WithCancellation(cancellationToken).ConfigureAwait(false))
        {
            list.Add(item);
        }

        return list;
    }
}

首先,它返回一个ValueTask。其次,它确保观察到并ConfigureAwait(false)使用取消,以防止死锁。最后,如果源已经提供了自己的ToListAsync实现,则操作员将遵循该实现。

推荐阅读
手机用户2402851155
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有