An ambiguous workaround for tiered management?

I have a base class called an animal, and a dog and cat that are inherited from Animal. And a multi-level class called dogcat, which is inherited from the dog and cat, in Animal I have a method called sleep. When I want to use this method with dogcat, I get the "DogCat :: sleep" error message ambiguously, I understand the problem, but I read in the book that it should be possible when you declare a dream as virtual - but this does not work.

Is it possible that the book is incorrect or is there any workaround?

class Animal { public: Animal(){} virtual void sleep() { cout << "zzzzzzzzz" << endl; } virtual void eat() = 0; }; class Dog: public Animal { protected: Dog(){} virtual void eat() override { cout << "eats dogfood" << endl; } }; class Cat :public Animal { public: Cat(){} virtual void eat() override { cout << "eats catfood" << endl; } }; class DogCat : public Dog, public Cat { public: DogCat(){} using Dog::eat; }; int main(int argc, char** argv) { DogCat *DC = new DogCat(); DC->sleep();//Error } 
+5
source share
2 answers

You have a problem

enter image description here

The “diamond problem” (sometimes called the “deadly death diamond” [4]) is the ambiguity that occurs when two classes B and C inherit from A and class D inherits from both B and C. If there is a method in A Since B and C are overridden, and D does not override it, then which version of the method inherits D: B or C?

So. You now have two options A. What is the solution? You have two:

  • Define a sleep operation in one of the subclasses and name it:
 class Cat :public Animal { public: Cat(){} virtual void eat() override { cout << "eats catfood" << endl; } void sleep() { Animal::sleep(); } }; int main(int argc, char** argv) { DogCat *DC = new DogCat(); DC->Cat::sleep(); } 
  1. Use virtual inheritance, as @Asesh says. The problem is the common eat () method. You must override it.
+6
source

You must use virtual inheritance

 class Animal { public: Animal(){} virtual void sleep() { cout << "zzzzzzzzz" << endl; } virtual void eat() = 0; }; class Dog: virtual public Animal { protected: Dog(){} virtual void eat() override { cout << "eats dogfood" << endl; } }; class Cat : virtual public Animal { public: Cat(){} virtual void eat() override { cout << "eats catfood" << endl; } }; class DogCat : public Dog, public Cat { public: DogCat(){} using Dog::eat; }; int main(int argc, char** argv) { DogCat *DC = new DogCat(); DC->sleep();//Error } 
+3
source

Source: https://habr.com/ru/post/1257932/


All Articles