-4

class diagram

class A {public: virtual int func();};
class B: virtual public A {};
class C: virtual public A {};
class D: virtual public C {public: virtual int func();};
class E: public B, public D {}; 
// e is an object of E
e->func(); // this will run func defined in A, not in D

I have a multiple inheritance situation as in the above example. How can I implement this to call the most derived method? (To call func() implemented in D, not in A, when I write e->func())

Cœur
  • 37,241
  • 25
  • 195
  • 267

2 Answers2

1

When I test your example I get "D" not "A" as you mentioned.

class A {public: virtual void func() {std::cout << "A" << std::endl;} };
class B: virtual public A {};
class C: virtual public A {};
class D: virtual public C {public: virtual void func() {std::cout << "D" << std::endl;} };
class E: public B, public D {};

int main()
{
  E e {};
  e.func();
}

You have the "Diamond" problem.

   A  
 B   D  // only B or D can override A::func()  
   E    // can override A::func()

The tip of the Diamond is class A, and it has two classes that derive from it, "B" and "D", on each side of the diamond. Only one of the derived classes that are part of the sides of the diamond can override a virtual function from the tip of the diamond, not both of them (Note that the bottom of the diamond can override, in this case E). In this case is class D which overrides func. If class B would override func it wouldn't compile. Also if class "B" and "D" don't override anything, in your example, A::func() would be called.

AdvSphere
  • 986
  • 7
  • 15
  • `D` does override `func` – M.M May 30 '18 at 02:35
  • 1
    Why -1? I stated "D" overrides func. – AdvSphere May 30 '18 at 02:37
  • 1
    For the ones assigning minus, please explain why. – AdvSphere May 30 '18 at 02:37
  • It is not true that "only one of the derive classes can override..." Also that hypothetical is not relevant to the question, since the question does actually have only one of the classes overriding (D). The question involves why the code calls `A::func`, your answer does not address this . – M.M May 30 '18 at 02:45
  • 1
    @M.M When you say "is not true that one of the derived classes can override", when I override with B (having D overriding as well) I get a compile error "no unique final overrider". Even when I test a simpler diamond problem I get the same error. Could you please explain why you are saying that's not true? – AdvSphere May 30 '18 at 02:48
  • Add a final overrider to E – M.M May 30 '18 at 02:49
  • @M.M E is not part of the sides of the diamond, is the bottom. I'll clarify this. – AdvSphere May 30 '18 at 02:51
  • `B` and `C` (and/or `D`) can both override so long as `E` also does – M.M May 30 '18 at 03:02
  • @M.M If E overrides is no longer diamond problem for that virtual function. Thank you for noting this. – AdvSphere May 30 '18 at 03:03
  • This all still has nothing to do with the question (in which D overrides and B does not). OP does not report a compilation error; there isn't any "problem" with the structure – M.M May 30 '18 at 03:04
1

If you have implemented func in D, that will be called. You can see the running example here

https://ideone.com/kwJubg

class A {public: virtual int func(){cout<<"In A";};};
class B: virtual public A {};
class C: virtual public A {};
class D: virtual public C {public: virtual int func(){cout<<"In D";};};
class E: public B, public D {}; 


int main()
{
    E *e = new E();
    e->func();    
    return 0;
}
Ankuj
  • 713
  • 3
  • 10
  • 27