I would like to use shared ptr to store an abstract class (A) inside of an other class (B), but I don't want to reveal that it will be stored in a shared ptr in B. Is it possible?
The reason I don't want to reveal it, because I think it is nicer if a constructor expects e.g a const reference to an object instead of a shared_ptr
An example:
class Renderer {
public:
void render() = 0;
};
class GLRenderer : public Renderer {
public:
void render() {}
};
class HeadlessRenderer : public Renderer {
public:
void render() {}
};
class Layer {
public:
Layer(const Renderer &renderer) {
// here is the problem that make_shared needs a concrete class
m_Renderer = std::make_shared<Renderer>(renderer);
}
private:
std::shared_ptr<Renderer> m_Renderer;
};
The most straightforward way to accomplish this would be if the abstract class defines a method that a subclass uses to clone itself, something like:
class Renderer {
public:
void render() = 0;
virtual Renderer *clone() const=0;
};
class GLRenderer : public Renderer {
public:
void render() {}
Renderer *clone() const { return new GLRenderer{*this}; }
};
And the constructor uses this:
Layer(const Renderer &renderer) : m_Renderer{renderer.clone()} {}
Note that every subclass now becomes responsible for overriding and implementing clone()
.
Alternatively, clone()
can return a std::shared_ptr
right off the bat, with each implementation of clone()
using std::make_shared
.