class Allocator
{
public:
virtual void * Alloc(size_t) = 0;
virtual void * Free(void*) = 0;
};
class Object
{
public:
Object() {}
virtual ~Object() {}
void * operator new (size_t size, Allocator * a, size_t extra)
{ return a->Alloc(size + extra); }
void operator delete (void * p, Allocator * a, size_t)
{ return a->Free(p); }
};
Object * obj = new (allocator, 10) Object;
Everything works great up to this point, my class' new overload is called
and the allocator's Alloc function is doing the allocation.
Now how do I delete the object? From what I've read, the syntax should be:
delete (obj, allocator, 0);
but this results in a compiler error: "'delete' : cannot delete objects that
are not pointers". This is because it's operating on the last parameter in
the list (the '0').
So I change it to:
delete (allocator, 0, obj);
This compiles and the destructor for Object is called, but the global delete
operator is then invoked and not the overloaded one (the parameters
'allocator' and '0' generate no code).
If I use:
delete obj;
This compiles, and it shouldn't. I should get something like
"Object::operator delete function does not take 0 arguments". But again, the
global delete operator is getting called after the destructors (exact same
behavior as the above invocation).
Now if I remove the virtual designation from the Object's destructor (which
I can't for this application) and use "delete obj;" syntax, I do get a
compiler error: "cannot delete pointers to objects of this type; the class
has no non-placement overload...".
Which is as it should be I'd think. I want to force the delete statements to
be 'proper' placement overloads. Why does the virtual destructor modify the
compiler's behavior here?
Now I can add this function to Object:
void Delete(Allocator * a)
{ operator delete (this, a, 0); }
And this allows you to delete obj like:
obj->Delete(allocator);
It both compiles and executes the overloaded destructor properly. But this
defeats the purpose of having a delete operator at all. I could just skip it
and have Delete() call a->Free() (except that the compiler will complain
about not having a matching delete overload).
So what's the deal here? What is the syntax for calling the overloaded
delete operator outside of a class member function? Am I stuck making the
destructor private and forcing obj->Delete to be called?
I'm using the Microsoft Visual C++ .NET 2003 compiler.