I have to register an object in a container upon its creation.
Without smart pointers I’d use something like this:
a_class::a_class()
{
register_somewhere(this);
}
With smart pointers I should use shared_from_this but I can’t use that in the constructor.
Is there a clean way to solve this problem? What would you do in a similar situation?
I’m thinking about introducing an init method to call just after creation and put everything in a factory function like this:
boost::shared_ptr<a_class> create_a()
{
boost::shared_ptr<a_class> ptr(new a_class);
ptr->init();
return ptr;
}
Is it fine or there is a standard procedure to follow in such cases?
EDIT: Actually my case is more complex. I have 2 object which shall maintain pointers each other. So the truth is I’m not “registering” but creating another object (let’s say b_class) which requires this as a parameter. b_class receives this as a weak pointer and stores it.
I’m adding this because since you are giving me design advices (which are very appreciated) at least you can know what I’m doing:
a_class::a_class()
{
b = new b_class(this);
}
In my program a_class is an entity and b_class is one of the concrete classes representing the state (in the constructor it’s just the starting state). a_class needs a pointer to the current state and b_class needs to manipulate the entity.
a_class is responsible for creating and destroying b_class instances and thus maintains a shared_ptr to them but b_class need to manipulate a_class and thus maintains a weak pointer. a_class instance “survives” b_class instances.
Do you suggest to avoid using smart pointers in this case?
…
Given these two facts, there should be no danger that a
b_classinstance can attempt to access ana_classinstance after thea_classinstance has been destroyed as thea_classinstance is responsible for destroying theb_classinstances.b_classcan just hold a pointer to it’s associateda_classinstance. A raw pointer doesn’t express any ownership which is appropriate for this case.In this example it doesn’t matter how the
a_classis created, dynamically, part of a aggregated object, etc. Whatever createsa_classmanages its lifetime just asa_classmanages the lifetime of theb_classwhich it instantiates.E.g.
Note, in this toy example there is no need for a
shared_ptr, an object member would work just as well (assuming that you don’t copy your entity class).