0

I would like to have a concurrent collection which supports a blocking thread-safe Take operation, while the actual item taken is an item that satisfies a condition.

Something like:

private TheBlockingCollection<MyClass> _myCollection;

MyClass myItem = _myCollection.TakeItemWhere(item => item.Type.equals(something));

The final goal would be to take the item with the highest property value that currently exists in the collection. e.g. - Max

Is there such a built in collection?

If not, what would be the better alternative?

Liel
  • 2,407
  • 4
  • 20
  • 39
  • Would you expect it to go through all available items, taking whichever one matches the predicate first? Or block until the first item matches the predicate? – Jon Skeet Aug 15 '13 at 13:59
  • I *very* much doubt that you'll find anything built into the existing collections which will meet that requirement. It sounds like you possibly want to have *multiple* collections (one per type) and order each of those by priority. – Jon Skeet Aug 15 '13 at 14:05
  • I would have done that. But in my case the property is an int, that represents priority. so separation to multiple collection according to the value is not possible... – Liel Aug 15 '13 at 14:08
  • 1
    It sounds like you don't actually need this; it sounds like you could just have the underlying collection be a priority queue that provides the item with the highest priority without needing to specify a condition when taking an item. – Servy Aug 15 '13 at 14:11

1 Answers1

2

As Servy mentions in a comment above, you should use a Priority Queue with a BlockingCollection.

If you implement an appropriate IComparable<> interface for the types being stored in the collection, then when you dequeue items you will automatically get the item that is first according to the comparison interface you defined.

Microsoft have provided a sample ConcurrentPriorityQueue which implements IProducerConsumerCollection that you can use with a BlockingCollection.

You use it by first creating an instance of a ConcurrentPriorityQueue and then by creating the BlockingCollection using one of the constructors which accepts a IProducerConsumerCollection<T>, for example: http://msdn.microsoft.com/en-us/library/dd287133.aspx

You just need to pass the ConcurrentPriortyQueue to that constructor.

Matthew Watson
  • 104,400
  • 10
  • 158
  • 276