c# - TPL 数据流:为什么会出现以下阻塞?
问题描述
为什么调用Run()
阻塞而不返回?
它正确地打印以下输出,这是有道理的。因为我已经初始化了BatchBlock()
170 的大小并创建了 200 个 volapoint 对象。但为什么它不返回?
ConvertToVolaSurface
ConvertToVolaSurface
CalculateStrangles
CalculateStrangles
这是我正在使用的代码片段
class Pipeline
{
public void Run()
{
// Grouping block - Collect vola points until vola surface is full
var batchBlock1 = new BatchBlock<VolaPoint>(170);
// Execution block - Convert vola points to surface
var transformBlock0 = new TransformBlock<VolaPoint[], VolaSurface>(x => this.ConvertToVolaSurface(x));
// Execution block - Calculate strangles
var transformBlock1 = new TransformBlock<VolaSurface, VolaSurface>(x => this.CalculateStrangles(x));
var linkOptions = new DataflowLinkOptions()
{
PropagateCompletion = true
};
batchBlock1.LinkTo(transformBlock0, linkOptions);
transformBlock0.LinkTo(transformBlock1, linkOptions);
for (int i = 0; i <= 200; i++)
{
batchBlock1.Post(new VolaPoint());
}
batchBlock1.Complete();
transformBlock1.Completion.Wait();
}
private VolaSurface ConvertToVolaSurface(VolaPoint[] volapoints)
{
Debug.WriteLine("ConvertToVolaSurface");
return new VolaSurface();
}
private VolaSurface CalculateStrangles(VolaSurface volaSurface)
{
Debug.WriteLine("CalculateStrangles");
return volaSurface;
}
}
解决方案
你的最后一个块是一个TransformBlock
,转换块有一个输出缓冲区,它们必须为空Complete
。将您的最后一个块更改为 anActionBlock
并且await
不阻塞调用线程就完成了。
public async Task Run()
{
// Grouping block - Collect vola points until vola surface is full
var batchBlock1 = new BatchBlock<VolaPoint>(170);
// Execution block - Convert vola points to surface
var transformBlock0 = new TransformBlock<VolaPoint[], VolaSurface>(x => this.ConvertToVolaSurface(x));
// Execution block - Calculate strangles
var actionBlock1 = new ActionBlock<VolaSurface>(x => this.CalculateStrangles(x));
var linkOptions = new DataflowLinkOptions()
{
PropagateCompletion = true
};
batchBlock1.LinkTo(transformBlock0, linkOptions);
transformBlock0.LinkTo(actionBlock1, linkOptions);
for (int i = 0; i <= 200; i++)
{
batchBlock1.Post(new VolaPoint());
}
batchBlock1.Complete();
await actionBlock1.Completion;
}
现在,如果CalculateStrangles(x)
正在返回某些东西,那么您需要将最后一个转换块链接到其他东西,否则您将永远无法完成。
推荐阅读
- javascript - Buttons on HTML Page not working in Safari / on iPhone
- web - Stuttering SignalR When Using IIS
- amazon-web-services - Does dynamodb global replace the whole item during sync?
- sql - 如何将包含多个“STRING_AGG”的查询转换为“FOR XML PATH”?
- swift - 在swift中使用Google place api时出错
- amazon-web-services - 使用 HTTP 错误代码 (503) 在两个 AWS Auto Scaling 组之间自动切换蓝/绿
- kubernetes - nginx 入口控制器在添加 - -default-ssl-certificate=default/certificate-name 标志后进入 CrashLoopBackOff 状态
- javascript - 未捕获的错误:目标容器不是 DOM 元素。反应.js
- reactjs - 无法在 allMarkdownRemark graphql 上查询字段
- r - 我想使用 R 的任何其他函数而不是 sprintf 来计算列表组