I have a very large, spread out class that is essentially a very contrived two dimensional linked list. I want to be able to "compile" it, by which I mean I want to finalize the list, so that only read accesses may be made, and then move all the elements into contiguous memory spaces. My rough solution is this:
#include <new>
...
MyListNode* pool = new MyListNode[length];
new(&pool[position]) MyListNode();
The trouble is that I essentially have two classes, one allocated with new and the other allocated with this method up here, and when I try to delete any of the objects allocated by the above method, glibc kills the program because of an invalid pointer.
The natural s开发者_开发百科olution is to create two classes, and just use runtime polymorphism to provide one interface but two implementation, etc. Is there any way that the memory standard in C++ permits this kind of jiggery pokery?
The obvious possibility would be to check the address of the object, and only delete it if if falls outside your pool. If I were doing it, I think I'd probably overload operator new
for the class, and have it always allocate space from your pool. This way you get your contiguous allocation without copying, and your objects are allocated uniformly so you can delete them uniformly as well.
Are you calling delete
on one of the objects in your array? Or are you manually invoking the destructor to mirror the placement new?
Since you have one call to non-placement new, you should only have one call to delete. And since you have n-calls to placement-new, you should manually invoke the destructor n times.
So, you may want something like this:
// Allocate an array of chars instead of an array of MyListNode. Since we
// are going to use placement new, this is necessary if MyListNode has a
// a default constructor
MyListNode* pool = static_cast<MyListNode *>(new char[sizeof(MyListNode) * length);
for (size_t position = 0; position < length; ++position)
new(&pool[position]) MyListNode();
...
for (position = 0; position < length; ++position)
pool[position].~MyListNode()
delete[] static_cast<char *>(pool);
精彩评论