简体   繁体   中英

Resolving circular dependencies from inheritance

Is it not possible to include the baseclass header and have it include all of its subclasses through it?

I seem to have come to an circular dependency with my base class and its subclasses.

From the program entry, I need to initialize one of the subclasses based on user input. I thought I could include the header of the base class which includes the headers of the subclasses:

main.cpp

#include "baseclass.h"

int main()
{
    ...
}

baseclass.h

#include "sub1.h"

class Base
{
    public:
        int name;
};

sub1.h

#include "baseclass.h"

class Base; // forward declaration

class Sub : public Base
{
    public:
        int age;
};

So the dependency is:

main -> baseclass -> sub1 -> baseclass -> sub1 -> etc...

If I keep the forward declaration in, g++ -std=c++11 -o prog *.cpp throws:

error: invalid use of incomplete type 'class Base'

Removing:

error: expected class-name before '{' token {

Not sure how to resolve this without putting a middle "factory" that includes all the subclass headers which each include the baseclass header.

Remove the #include "sub1.h" from baseclass.h , and create a separate header file, which includes all the derived classes you need, and include this header file into main.cpp.

Note: this line class Base; // forward declaration class Base; // forward declaration is not needed.

Remove #include "sub1.h" from base.h (also the class Base forward declaration). Where you wan't to use sub include sub1.h , in this case in the main. If you are actually building a bunch of sub type child classes then in all likelihood you will implement something to create them correctly anyway. That something would probably be a factory . It will look something like this:

// ClassFactory.h
#include "sub1.h"
#include "sub2.h"
...
#include "subN.h"

std::unique_ptr<Base> createClass(std::string name) {

    if (name == "sub1")
        return std::unique_ptr<Base>(new sub1());
    if (name == "sub2")
        return std::unique_ptr<Base>(new sub1());
    ...
    return nullptr;
}

And your main will include and use this file:

#include "ClassFactory.h"

int main(int argc, char** argv)
{
    ...
    std::unique_ptr<Base> myClass = createClass(argv[1])

Big note: All pseudo code .

Then you will have solved the problem of creating a complex set of child classes at runtime and your problem of how to include all of them.

If you want base.h to include sub1.h , that is possible only after the definition of class Base :

#ifndef BASE_H_
#define BASE_H_

class Base
{
    public:
        int name;
};

#include "sub1.h"
#endif

It's obvious that this removes the need for a forward declaration of Base ; at the point of inclusion it's fully defined.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM