【问题标题】:tpl dataflow: fixed buffer size without throwing items awaytpl 数据流:固定缓冲区大小而不会丢弃项目
【发布时间】:2013-09-17 09:54:07
【问题描述】:

在玩过数据流之后,我遇到了一个新问题。我想限制所有块的输入队列。我的生产块 (ActionBlock) 正在快速创建 5000 个元素并将它们发布到广播块。因此,如果我将广播块的 BoundedCapacity 设置为 100,他会丢弃大量数据。但我更希望生产块等待缓冲区块的输入队列中的新插槽。

有什么办法可以解决这个问题?

【问题讨论】:

标签: c# .net task-parallel-library tpl-dataflow


【解决方案1】:

这正是BufferBlock 的用途。如果您设置它的BoundedCapacity 并且它已满,它将推迟接收任何消息,直到有人消费它们。这意味着例如Post() 将阻塞,SendAsync() 将返回一个未完成的Task

编辑:没有内置块可以发送到多个目标并且从不丢弃数据。但是您可以通过ActionBlock 和发送循环轻松地自己构建一个:

static ITargetBlock<T> CreateMultipleTargetsBlock<T>(
    IEnumerable<ITargetBlock<T>> targets, int boundedCapacity)
{
    var targetsList = targets.ToList();

    var block = new ActionBlock<T>(
        async item =>
        {
            foreach (var target in targetsList)
            {
                await target.SendAsync(item);
            }
        },
        new ExecutionDataflowBlockOptions { BoundedCapacity = boundedCapacity });

    // TODO: propagate completion from block to targets

    return block;
}

此代码假定您不需要为每个目标克隆数据并且目标列表永远不会更改。修改代码应该相当简单。

【讨论】:

  • 首先 - 谢谢。我绝对是瞎了眼......但我需要一个块,它可以向多个接收者发送消息。缓冲块是不可能的。知道如何解决这个问题吗?
  • 当其中一个接收器速度慢时会发生什么?是否应该要求其他接收者等待它? (我假设接收者也设置了BoundedCapacity,否则,在缓冲区上设置BoundedCapacity 基本上没有效果。)
  • 是的,BoundedCapacity 总是相同的值。这也是事实,其他接收者需要等待缓慢的操作。
  • 根据我的经验,当BufferBlock 满员调用时,Post() 不会阻塞。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-11-26
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多