I am looking for a (possibly) better approach to solve a problem with abstract classes. This question is more about an alternative design than the implementation provided here (I willingly simplified it).
I have a basic Content
interface class like this:
class Content {
public:
virtual void info() = 0;
};
class ContentA : public Content {
public:
void info() override { cout << "Content A" << endl; }
int serial() { return 123; }
int num() { return 456; }
};
class ContentB : public Content {
public:
void info() override { cout << "Content B" << endl; }
int identifier() { return 789; }
};
I have a Container
class interface which has to contain a Content
object:
class Container {
public:
virtual shared_ptr<Content> content() = 0;
virtual void info() = 0;
void contentInfo() { content()->info(); }
};
class ContainerA : public Container {
public:
ContainerA(shared_ptr<ContentA> content) : m_content(content) {}
shared_ptr<Content> content() { return m_content; }
void info() {
auto identifier = m_content->serial() * m_content->num();
cout << "Container A: " << identifier << endl;
}
protected:
shared_ptr<ContentA> m_content;
};
class ContainerB : public Container {
public:
ContainerB(shared_ptr<ContentB> content) : m_content(content) {}
shared_ptr<Content> content() { return m_content; }
void info() {
cout << "Container B: " << m_content->identifier() << endl;
}
protected:
shared_ptr<ContentB> m_content;
};
Usage example would be:
auto contentB = make_shared<ContentB>();
ContainerB containerB(contentB);
containerB.info();
// => "Container B: 789"
containerB.contentInfo();
// => "Content B"
Although ContentA
and ContentB
both inherit from Container
, they have their own specialized methods intended to be specifically used by ContainerA
and ContainerB
respectively. ContainerA
can only interact with ContentA
, and ContainerB
can only interact with ContentB
. You can't instantiate ContainerA
by passing a ContentB
to its constructor.
I want to enforce the fact that, in the future, anyone needing to create ContainerC
will also need first to create ContentC
. This is why the content()
method is virtual pure.
I'm not sure using such content()
method is the correct way to do this. Is it? I don't know. You can test it on Ideone here.
Basically, I thought it would reduce repetition if m_content
was a member of the abstract class Container
. But by doing so, it won't compile as the exact Content
inherited class is not known from the Container
. That would required casting the content object, which is worse. See what I mean here.
Aucun commentaire:
Enregistrer un commentaire