TransformManyBlockTInput TOutput

(SelectMany,1-m:這個對映的結果是扁平的,就像 LINQ 的 SelectMany 一樣)

TransformManyBlock <TInput,TOutput>與 TransformBlock <TInput,TOutput>非常相似。
關鍵區別在於,TransformBlock <TInput,TOutput>為每個輸入生成一個且僅一個輸出,而 TransformManyBlock <TInput,TOutput>為每個輸入生成任意數量(零個或多個)輸出。與 ActionBlock 和 TransformBlock <TInput,TOutput>一樣,可以使用委託指定此處理,用於同步和非同步處理。

Func <TInput,IEnumerable>用於同步,Func <TInput,Task <IEnumerable >>用於非同步。與 ActionBlock 和 TransformBlock <TInput,TOutput>一樣,TransformManyBlock <TInput,TOutput>預設為順序處理,但可以另外配置。

對映委託返回一組專案,這些專案單獨插入到輸出緩衝區中。

StackOverflow 文件

非同步 Web 爬蟲

var downloader = new TransformManyBlock<string, string>(async url =>
{
    Console.WriteLine(“Downloading “ + url);
    try 
    { 
        return ParseLinks(await DownloadContents(url)); 
    } 
    catch{}
    
    return Enumerable.Empty<string>();
});
downloader.LinkTo(downloader);

將可列舉擴充套件為其組成元素

var expanded = new TransformManyBlock<T[], T>(array => array);

通過從 1 到 0 或 1 個元素進行過濾

public IPropagatorBlock<T> CreateFilteredBuffer<T>(Predicate<T> filter)
{
    return new TransformManyBlock<T, T>(item =>
        filter(item) ? new [] { item } : Enumerable.Empty<T>());
}

Stephen Toub 介紹 TPL 資料流