On 06/10/2011 10:01 PM, Christopher wrote:
Got a complaint that allocation is costly for 2000 items to be
inserted into a set one by one. I need to preallocate, and depend on
the set growing, if needed, after the number of items exceeds the
preallocation.
Do I do so like this?
class A
{
public:
A()
{
m_values.get_allocator.allocate(2000);
}
~A()
{
// Does set still clean up after itself?
}
typedef std::pair<unsigned, std::smart_ptr> Value;
typedef std::set<Value> Values;
Values m_values;
}
No, not really. Allocators have something called 'rebind'.
Basically a set gets an allocator of T, and rebinds it to allocator
of its own internal type to carry its [meta]data.
Since these are templates, the two allocators differ in c++ type.
If you think you can outdo the standard allocators, you need to
invest into allocator requirements first, to get the formalities right;
then you need to make your allocator perform well. Take a look
at new_allocator (simple allocator just calling ::new).
Maybe there are other ways, but if you know the characteristics
of this set's usage, e.g. a set will contain 2000 elements,
then they will be mainly constant in size, you could optimise by
preallocating. Or preallocating in chunks as needed.
It's just a bit too hairy templated stuff to do so for no reason,
and not so easy to get a really good performance out of it.
Explore first; [1] is a rather easy way to start.
BTW, do you need a set? Maybe a hashset? Maybe a vector?
Edek
[1]http://www.boost.org/doc/libs/1_44_0/libs/pool/doc/interfaces.html- Hi=
Container needs to act like a queue more or less. I fill it with items
from the container. However, the container has to guarentee that the
items are unique. Because the methods where they are used may receive
operations on them.