Search code examples
c++abstract-classinternal-class

How can I implement internal abstract member classes in c++?


An abstract class has internal virtual functions. Can an abstract class have internal virtual classes to be implemented later?

I tried the following:

#include <bits/stdc++.h>
using namespace std;

class C1 {
    public:
        class Child {
            int tmp;
            virtual int getint() = 0;
        };
    virtual Child getChild() = 0;
};

class C2: public C1 {
    public:
        class Child {
            int getint()
            {
                return 10;
            }
        } c;
    Child getChild()
    {
        return c;
    }
};

int main() { return 0; }

Child is an abstract class which will be overrode in derived classes. And I hope the implemented Child can be used to define a function.

However, I got an error:

invalid abstract return type for member function 'virtual C1::Child C1::getChild()'

Can't I implement an internal abstract class in derived classes, just like implementing a virtual function?


Solution

  • In the present code, class C1::Child and class C2::Child have no inheritance relationship. Hence they are totally unrelated classes. Even if you relate them with inheritance, then also getChild() cannot return Child (value). It can return either Child& (reference) or Child* (pointer) to form a valid virtual methods with covariance. Refer: C++ virtual function return type

    Such errors are easily caught by using override specifier available in C++11.

    Without knowing the exact context of what you are trying to achieve, the possible code should look like this:

    class C1 {
      // ... same
      virtual Child& getChild() = 0;
      //      ^^^^^^ reference
    };
    
    class C2 : public C1 {
    //         ^^^^^^ did you miss this?
    public:
      class Child : public C1::Child {
      //                   ^^^^^^^^^ inheritance
        int getint() override { return 10; }
      } c;
      Child& getChild() override { return c; }
    };
    

    Also your below statement seems confusing:

    "Child is a abstract class, which will be implemented later,"

    Like virtual methods, the classes don't have such runtime relationships.
    The best meaning of "implementing later" in the context of class is -- implementing it outside the body of the enclosing class, such as:

    class Outer { public: class Inner; };
    // ...
    class Outer::Inner { ... };