How to avoid game objects accidentally deleting themselves in C++
- by Tom Dalling
Let's say my game has a monster that can kamikaze explode on the player. Let's pick a name for this monster at random: a Creeper. So, the Creeper class has a method that looks something like this:
void Creeper::kamikaze() {
EventSystem::postEvent(ENTITY_DEATH, this);
Explosion* e = new Explosion;
e->setLocation(this->location());
this->world->addEntity(e);
}
The events are not queued, they get dispatched immediately. This causes the Creeper object to get deleted somewhere inside the call to postEvent. Something like this:
void World::handleEvent(int type, void* context) {
if(type == ENTITY_DEATH){
Entity* ent = dynamic_cast<Entity*>(context);
removeEntity(ent);
delete ent;
}
}
Because the Creeper object gets deleted while the kamikaze method is still running, it will crash when it tries to access this->location().
One solution is to queue the events into a buffer and dispatch them later. Is that the common solution in C++ games? It feels like a bit of a hack, but that might just be because of my experience with other languages with different memory management practices.
In C++, is there a better general solution to this problem where an object accidentally deletes itself from inside one of its methods?