-1

To break a circular dependency between classes, the traditional approach is to seperate declaration and definition and forward-declare a class where needed. However, forward declaration is not possible when two classes inheriting from the same base class depend on each other, as the compiler needs to see the declaration of methods to do inheritance.

Here's what it looks like.

// Base.hpp
class Base {
    public:
    virtual ~Base() = default;
    void foo();
};
// DerivedA.hpp
#include "Base.hpp"

class DerivedB;

class DerivedA : public Base {
    public:
    void bar(DerivedB& b);
};
// DerivedB.hpp
#include "Base.hpp"

class DerivedA;

class DerivedB : public Base {
    public:
    void baz(DerivedA& a);
};

Then, when I try to implement DerivedA or DerivedB:

// DerivedA.cpp
#include "DerivedA.hpp"
#include "DerivedB.hpp" // ERROR: redeclaration of Base

void DerivedA::bar(DerivedB& b) {
    b.foo();
}

I can't find any way out of this except for a large change in code structure. Is there a better way?

Yizhe Sun
  • 43
  • 6
  • just put your definitions in your header files (at least Base.hpp) inside a `#ifndef xxx / #define XX / ... / #endif", see my answer – bruno Apr 03 '19 at 11:22
  • 1
    What resource do you use to learn C++? If at the very moment it introduces header files it does not also mention include guards, burn it and switch to a different book/tutorial whatever. – sebrockm Apr 03 '19 at 11:31
  • @sebrockm I misunderstood the header guards. I thought that if I include a header guard in Base.hpp, then one of the derived class won't be able to receive a copy of Base.hpp – Yizhe Sun Apr 03 '19 at 11:36

1 Answers1

4

protect definition in headers against multiple inclusions, for instance :

#ifndef _BASE_HPP
#define _BASE_HPP

// Base.hpp
class Base {
  public:
  virtual ~Base() = default;
  void foo();
};

#endif

when #include "DerivedA.hpp" _BASE_HPP is not yet defined so the definition of the class Base is read but in #include "DerivedB.hpp" _BASE_HPP is defined so the class definition is not again read

bruno
  • 32,421
  • 7
  • 25
  • 37