- android - RelativeLayout 背景可绘制重叠内容
- android - 如何链接 cpufeatures lib 以获取 native android 库?
- java - OnItemClickListener 不起作用,但 OnLongItemClickListener 在自定义 ListView 中起作用
- java - Android 文件转字符串
我有一个 BlockingCollection .生产者任务向其中添加项目,消费者任务移除项目。
现在我想限制集合中的项目数量,如果添加了更多项目,则自动丢弃旧数据。该集合不应同时包含超过 N
个最近添加的项目。
因此,如果生产者添加新项目的速度比消费者移除新项目的速度快,我希望消费者只处理最新的项目。
我可以在其构造函数中限制 BlockingCollection
的大小,但这当然意味着它会在添加更多项目时阻塞,而不是删除旧项目。
(我不想在生产者端阻塞,只有消费者端在从空集合中检索项目时应该阻塞。)
我目前的解决方案是 hack,并且只适用于 1 的大小限制:
(而且我不太确定它是否可靠。)
// My consumer task:
foreach (var item in blockingCollection.GetConsumingEnumerable())
{
var lastItem = item;
var lastItemTmp = item;
while (blockingCollection.TryTake(out lastItemTmp))
lastItem = lastItemTmp;
// Now lastItem contains the most recent item in the collection,
// and older items have been discarded.
// Proceed consuming lastItem ...
}
是否有更清洁的解决方案?
最佳答案
这样做:
void AddItemToQueue(MyClass item)
{
while (!queue.TryAdd(item))
{
MyClass trash;
queue.TryTake(out trash);
}
}
如果在您尝试添加项目时队列已满,则会从队列中删除一个项目。它使用 TryTake
因为有可能(不太可能,但有可能)其他线程可能在您有机会取一个之前从队列中删除了最后一个项目。
当然,这假设您在构造 BlockingCollection
时指定了项目数量限制。
实现此目的的另一种方法是创建您自己的循环队列类,并让它实现 IProducerConsumerCollection界面。然后,您可以使用该类的实例作为 BlockingCollection
的后备集合。实现循环队列并不是特别困难,尽管有些边缘情况很难正确处理。而且您必须使它成为并发数据结构,尽管使用锁很容易做到这一点。
如果您不希望队列经常溢出,或者如果队列的流量非常低(即每秒不会被命中数千次),那么我最初的建议将按照您的意愿行事并且不会性能问题。如果存在性能问题,那么循环队列就是解决方案。
关于c# - 丢弃旧数据的 BlockingCollection,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21905740/
我有两个阻塞集合 - 一个优先级高于另一个。如果我使用 TryTakeFromAny 并首先指定更高优先级的 BlockingCollection,是否可以保证首先查看更高优先级的队列? 最佳答案 这
我有一个使用 BlockingCollection<> 实现的下载队列.现在我想偶尔优先考虑一些下载。我认为将某些元素“向上”移动到集合中可能会很棒,例如在列表中,但没有像 Remove()/AddF
BlockingCollection.Dispose实际上做什么? 最佳答案 这样可以正确处理内部等待 handle 。 BlockingCollection在内部使用一对事件等待句柄,它们又具有关联
BlockingCollection blockingCollection = new BlockingCollection(); // create and start a producer
将来自多个线程的消息放到一个队列中并让一个单独的线程一次处理一个队列中的项目的最佳方法是什么? 在尝试断开多个线程的事件时,我经常使用这种模式。 我正在为此使用 BlockingCollection,
我正在尝试正确建模多线程单生产者/多消费者场景,其中消费者可以要求生产者获取元素,但生产者需要执行耗时的操作来生产它(想想执行查询或打印文档)。 我的目标是确保没有消费者可以同时要求生产者生产一件商品
我知道使用 ConcurrentQueue 的 BlockingCollection 的 boundedcapacity 为 100。 但是我不确定那是什么意思。 我正在尝试实现一个并发缓存,如果队列
BlockingCollection 仅包含添加单个项目的方法。如果我想添加一个集合怎么办?我应该只使用 foreach 循环吗? 为什么 BlockingCollection 不包含添加集合的方法?
我正在编写一个 WCF 服务,它从多个模块(数据库、其他服务..)接收通知并将它们添加到阻塞集合中,以便在将相关数据发布到客户端的使用者线程上进行处理。 客户端可以请求存储在服务器上的完整数据,在此操
我有这样一种情况,我需要有大量(数百个)队列,其中的项目应该按顺序处理(需要单线程消费者)。我的第一个实现,based on the samples,我为每个 BlockingCollection 使
Stephen Toub 的书第 88 页 http://www.microsoft.com/download/en/details.aspx?id=19222 有代码 private Blockin
我即将使用如下所示的 BlockingCollection,只是想检查它是否适合线程安全等。想知道我是否需要 CancellationTokenSource。 谢谢 public class MyAp
你好,我正在尝试创建一个使用流数据的应用程序......(所以没有结束......完成......等) 由于它的性质,因为流数据得到了很多操作,我使用 BlockingCollection,它工作得很
我有一个 BlockingCollection .生产者任务向其中添加项目,消费者任务移除项目。 现在我想限制集合中的项目数量,如果添加了更多项目,则自动丢弃旧数据。该集合不应同时包含超过 N 个最近
我有一个线程将项目添加到 BlockingCollection 。 在我正在使用的另一个线程上foreach(myCollection.GetConsumingEnumerable() 中的 var
我有一个程序如下 class Program { public static int TaskCount { get; set; } public stati
我有以下代码,其中包含一个生产者线程和多个消费者线程。你知道多个消费者是否是线程安全的。例如,线程 1 是否有可能正在消费,而线程 2 是否并行消费并更改线程 1 中使用的项目的值? namespac
我需要建立一个阻塞优先级队列,我的预感是 TakeFromAny 可能是 secret 成分,但是关于该方法的文档很少。它的目的/适当用途是什么? 我的要求是多个线程将添加到高优先级或低优先级队列中。
有没有办法删除 具体 BlockingCollection 中的项目,如下所示: IMyItem mySpecificItem = controller.getTopRequestedItem();
我试图在.NET 4上新的Parallel Stacks的背景下理解BlockingCollection的目的。 MSDN文档说: BlockingCollection用作IProducerConsu
我是一名优秀的程序员,十分优秀!