Notice: This page requires JavaScript to function properly.
Please enable JavaScript in your browser settings or update your browser.
Aprende Herencia Diamante | Visión General de la Herencia
POO en C++
course content

Contenido del Curso

POO en C++

POO en C++

1. Fundamentos de la POO en C++
2. Constructores y Destructores
3. Visión General de la Encapsulación
4. Visión General de la Herencia
5. Visión General del Polimorfismo

book
Herencia Diamante

La herencia múltiple puede conducir a una situación conocida como el problema del diamante o herencia en diamante, que representa un desafío importante en los lenguajes de programación orientados a objetos que admiten herencia múltiple.

Esto ocurre cuando una subclase hereda de dos o más classes, que a su vez heredan de una superclase común. El término diamante se utiliza porque el esquema de herencia se asemeja a la forma de un diamante.

main.cpp

main.cpp

copy
1234567
class Base {}; class Derived1 : public Base {}; class Derived2 : public Base {}; class Diamond : public Derived1, public Derived2 {};

El principal problema de la herencia en diamante es la ambigüedad que genera. Dado que Diamond hereda tanto de Derived1 como de Derived2, que a su vez heredan de Base, existen dos copias de Base dentro de un objeto de Diamond. Esto puede provocar ambigüedad.

main.cpp

main.cpp

copy
12345678910111213141516
#include <iostream> class Base { public: void display() { std::cout << "Base display()" << std::endl; } }; class Derived1 : public Base { }; class Derived2 : public Base { }; class Diamond : public Derived1, public Derived2 { }; int main() { Diamond obj; obj.display(); // Ambiguity: Which display() method should be called? }

Solución al problema

La palabra clave virtual ayuda a evitar este problema. Puede abordar esta ambigüedad mediante la herencia virtual utilizando la palabra clave virtual. Cuando Diamond hereda de forma virtual, C++ garantiza que solo haya una copia de la superclase, incluso si se hereda varias veces a través de diferentes rutas.

main.cpp

main.cpp

copy
1234567
class Base {}; class Derived1 : virtual public Base {}; class Derived2 : virtual public Base {}; class Diamond : public Derived1, public Derived2 {};
Note
Nota

Intenta resolver el problema de ambigüedad en el ejemplo anterior utilizando la herencia virtual.

Implementación de la herencia diamante

Para implementar la herencia diamante de manera efectiva, utiliza la palabra clave virtual en la declaración de la superclase dentro de las classes intermedias. Asegúrate de un uso consistente de la herencia virtual en todos los caminos de la jerarquía de herencia y presta atención al orden de llamadas de constructores y destructores.

Resolución de ambigüedades

Uno de los desafíos de la herencia múltiple es también tratar con posibles ambigüedades cuando se trata de miembros con los mismos nombres.

main.cpp

main.cpp

copy
12345678910111213141516171819
#include <iostream> class Base {}; class Derived1 : public Base { public: void display() { std::cout << "Derived1 display()" << std::endl; } }; class Derived2 : public Base { public: void display() { std::cout << "Derived2 display()" << std::endl; } }; class Diamond : public Derived1, public Derived2 { }; int main() { Diamond obj; obj.display(); // Ambiguity: Which display() method should be called? }

Si ambas superclases tienen miembros con el mismo nombre, la subclase puede no saber cuál utilizar. Para resolver tales ambigüedades, se puede utilizar el operador de resolución de ámbito (::) para especificar a qué miembro de la clase base se desea acceder. Por ejemplo:

main.cpp

main.cpp

copy
1234567891011121314151617181920
#include <iostream> class Base {}; class Derived1 : public Base { public: void display() { std::cout << "Derived1 display()" << std::endl; } }; class Derived2 : public Base { public: void display() { std::cout << "Derived2 display()" << std::endl; } }; class Diamond : public Derived1, public Derived2 { }; int main() { Diamond obj; obj.Derived1::display(); obj.Derived2::display(); }
question mark

¿Cuál es el principal problema causado por la herencia en diamante?

Select the correct answer

¿Todo estuvo claro?

¿Cómo podemos mejorarlo?

¡Gracias por tus comentarios!

Sección 4. Capítulo 5

Pregunte a AI

expand

Pregunte a AI

ChatGPT

Pregunte lo que quiera o pruebe una de las preguntas sugeridas para comenzar nuestra charla

course content

Contenido del Curso

POO en C++

POO en C++

1. Fundamentos de la POO en C++
2. Constructores y Destructores
3. Visión General de la Encapsulación
4. Visión General de la Herencia
5. Visión General del Polimorfismo

book
Herencia Diamante

La herencia múltiple puede conducir a una situación conocida como el problema del diamante o herencia en diamante, que representa un desafío importante en los lenguajes de programación orientados a objetos que admiten herencia múltiple.

Esto ocurre cuando una subclase hereda de dos o más classes, que a su vez heredan de una superclase común. El término diamante se utiliza porque el esquema de herencia se asemeja a la forma de un diamante.

main.cpp

main.cpp

copy
1234567
class Base {}; class Derived1 : public Base {}; class Derived2 : public Base {}; class Diamond : public Derived1, public Derived2 {};

El principal problema de la herencia en diamante es la ambigüedad que genera. Dado que Diamond hereda tanto de Derived1 como de Derived2, que a su vez heredan de Base, existen dos copias de Base dentro de un objeto de Diamond. Esto puede provocar ambigüedad.

main.cpp

main.cpp

copy
12345678910111213141516
#include <iostream> class Base { public: void display() { std::cout << "Base display()" << std::endl; } }; class Derived1 : public Base { }; class Derived2 : public Base { }; class Diamond : public Derived1, public Derived2 { }; int main() { Diamond obj; obj.display(); // Ambiguity: Which display() method should be called? }

Solución al problema

La palabra clave virtual ayuda a evitar este problema. Puede abordar esta ambigüedad mediante la herencia virtual utilizando la palabra clave virtual. Cuando Diamond hereda de forma virtual, C++ garantiza que solo haya una copia de la superclase, incluso si se hereda varias veces a través de diferentes rutas.

main.cpp

main.cpp

copy
1234567
class Base {}; class Derived1 : virtual public Base {}; class Derived2 : virtual public Base {}; class Diamond : public Derived1, public Derived2 {};
Note
Nota

Intenta resolver el problema de ambigüedad en el ejemplo anterior utilizando la herencia virtual.

Implementación de la herencia diamante

Para implementar la herencia diamante de manera efectiva, utiliza la palabra clave virtual en la declaración de la superclase dentro de las classes intermedias. Asegúrate de un uso consistente de la herencia virtual en todos los caminos de la jerarquía de herencia y presta atención al orden de llamadas de constructores y destructores.

Resolución de ambigüedades

Uno de los desafíos de la herencia múltiple es también tratar con posibles ambigüedades cuando se trata de miembros con los mismos nombres.

main.cpp

main.cpp

copy
12345678910111213141516171819
#include <iostream> class Base {}; class Derived1 : public Base { public: void display() { std::cout << "Derived1 display()" << std::endl; } }; class Derived2 : public Base { public: void display() { std::cout << "Derived2 display()" << std::endl; } }; class Diamond : public Derived1, public Derived2 { }; int main() { Diamond obj; obj.display(); // Ambiguity: Which display() method should be called? }

Si ambas superclases tienen miembros con el mismo nombre, la subclase puede no saber cuál utilizar. Para resolver tales ambigüedades, se puede utilizar el operador de resolución de ámbito (::) para especificar a qué miembro de la clase base se desea acceder. Por ejemplo:

main.cpp

main.cpp

copy
1234567891011121314151617181920
#include <iostream> class Base {}; class Derived1 : public Base { public: void display() { std::cout << "Derived1 display()" << std::endl; } }; class Derived2 : public Base { public: void display() { std::cout << "Derived2 display()" << std::endl; } }; class Diamond : public Derived1, public Derived2 { }; int main() { Diamond obj; obj.Derived1::display(); obj.Derived2::display(); }
question mark

¿Cuál es el principal problema causado por la herencia en diamante?

Select the correct answer

¿Todo estuvo claro?

¿Cómo podemos mejorarlo?

¡Gracias por tus comentarios!

Sección 4. Capítulo 5
some-alt