This is incredibly high number, you have to understand. Just to compare, List<int> takes 8 ms to create 100,000 items.

Let us see how it works when we use more of this.

100 items in 5ms = 0ms per item

1,000 items in 37ms = 0ms per item

10,000 items in 2,319ms = 0ms per item

Note the numbers, will you?

1,000 items in 37 ms, but 10,000 items? 2.3 seconds!

20,000 items in 21,331ms = 1ms per item

And doubling the amount took ten times as long?

25,000 items in 32,588ms = 1ms per item

And at this point, I stopped trying, because I didn’t have the patience.

Note that the other concurrent collection, ConcurrentStack, ConcurrentQueue and ConcurrentDictionary do not suffer from the same problem.

I contacted Microsoft about this, and this is already resolved in .NET 4.5. The underlying issue was that ThreadLocal, which ConcurrentBag uses, didn’t expect to have a lot of instances. That has been fixed, and now can run fairly fast.

Also the basic Concurrent classes like the ConcurrentDictionary if you create a ton of them (For example we used ConcurrentDictionary for some caching in each entity and profiling a bit we found the memory problem on the ConcurrentDictionary)

How is this testing concurrent bag? All I can see is you testing the constructor for concurrent bag by adding it to a list and not actually adding items to the bag or dealing with the bag. Is that the only issue? When you have 10000 bags created do they perform reasonably?

You do realize you're testing how many ConcurrentBag objects you can synchronously instantiate, not how many items you can put into a ConcurrentBag, right? What's an example use case for creating n ConcurrentBag objects in a loop? I can imagine adding n items to a ConcurrentBag, but not creating n ConcurrentBags.

Chris,
For example, we have state associated with queries in RavenDB, we initially put that state (for each unique query) inside a ConcurrentBag.
But it turns out that just the act of creating the bag can be the most expensive thing there.

ConcurrentBag is another word for memory leak. See http://stackoverflow.com/questions/10850443/concurrentbag-does-cause-memory-leak It is very difficult to use it right. Besides this it does consume waay more memory for simple data types like an integer. I have in general a problem with a type that keeps a disposable object (ThreadLocal) inside it but it does not implement the IDisposable interface. The only way to get rid of the threadlocals is to terminate the thread which did create the ConcurrentBag. This is still not fixed with .NET 4.5.