我听说,如果你使用的是 Post
方法,而不是 SendAsync
办法 ActionBlock<T>
对象,当你决定利用它的 BoundedCapacity
财产。
谁能解释一下为什么会这样?
该 Post
方法试图同步发布一个项目,并返回 true
或 false
,取决于该区块是否接受该项目。不接受一个项目的原因。
Complete
方法)。)Completion.IsCompleted
属性返回 true
).BoundedCapacity != -1
),其缓冲区目前已满。缓冲区的 SendAsync
方法试图异步发布一个项目并返回一个 Task<bool>
. 这个任务总是会被完成,除非该块的容量是有边界的,它的缓冲区当前是满的,而且它当前没有完成或标记为完成。只有在这种情况下,才会出现 SendAsync
将会异步行事。在等待任务后, bool
任务的结果表示该块是否接受该项目。不接受某项的原因。
SendAsync
,或在等待期间。SendAsync
在等待过程中,或由于异常情况,或由于它的 Fault
方法被调用。所以 Post
和 SendAsync
是点(3)。在有界容量的块和满缓冲区的情况下,它们的表现是不同的。在这种情况下 Post
立即拒绝该项目,而 SendAsync
将会在缓冲区再次有空闲空间时异步接受它。
在大多数情况下 SendAsync
是可取的。使用 Post
而非 SendAsync
可以看作是一个等待发生的bug,当一段时间后,块被重新配置为bounded,以解决新发现的与过度使用内存有关的问题。
最好不要否定这两个方法的返回值,因为返回值为 false
在大多数情况下,它表明一个错误。很少有期望并准备处理一个 false
结果。一些想法。
if (!block.Post(item)) throw new InvalidOperationException();
if (!await block.SendAsync(item)) throw new InvalidOperationException();
var accepted = block.Post(item); Debug.Assert(accepted);
var accepted = await block.SendAsync(item); Debug.Assert(accepted);
是的,你可以失去信息。Post
潜力较大,但 SendAsync
也会丢失信息。假设你有一个ActionBlock需要1000毫秒才能完成,在这个时间段内有10条消息被发布。BoundedCapacity
被设置为5的 ActionBlock
. 结果,最后5条信息没有处理,信息丢失。
下面是一些细节。TPL数据流,Post()和SendAsync()在功能上有什么区别?
请看第二个答案。