Polimorfismo C ++ con ejemplo

Tabla de contenido:

Anonim

¿Qué es el polimorfismo en C ++?

En C ++, el polimorfismo hace que una función miembro se comporte de manera diferente según el objeto que la llama / invoca. El polimorfismo es una palabra griega que significa tener muchas formas. Ocurre cuando tienes una jerarquía de clases relacionadas por herencia.

Por ejemplo, supongamos que tenemos la función makeSound (). Cuando un gato llama a esta función, producirá un maullido. Cuando una vaca invoca la misma función, proporcionará el sonido muuu.

Aunque tenemos una función, se comporta de manera diferente en diferentes circunstancias. La función tiene muchas formas; por tanto, hemos logrado el polimorfismo.

En este tutorial de C ++, aprenderá:

  • ¿Qué es el polimorfismo?
  • Tipos de polimorfismo
  • Compilar polimorfismo de tiempo
  • Sobrecarga de funciones
  • Sobrecarga del operador
  • Polimorfismo en tiempo de ejecución
  • Anulación de función
  • Función virtual C ++
  • Polimorfismo en tiempo de compilación vs. Polimorfismo en tiempo de ejecución

Tipos de polimorfismo

C ++ admite dos tipos de polimorfismo:

  • Polimorfismo en tiempo de compilación y
  • Polimorfismo en tiempo de ejecución.

Compilar polimorfismo de tiempo

Invoca las funciones sobrecargadas haciendo coincidir el número y el tipo de argumentos. La información está presente durante el tiempo de compilación. Esto significa que el compilador de C ++ seleccionará la función correcta en el momento de la compilación.

El polimorfismo en tiempo de compilación se logra mediante la sobrecarga de funciones y la sobrecarga del operador.

Sobrecarga de funciones

La sobrecarga de funciones ocurre cuando tenemos muchas funciones con nombres similares pero argumentos diferentes. Los argumentos pueden diferir en términos de número o tipo.

Ejemplo 1:

#include using namespace std;void test(int i) {cout << " The int is " << i << endl;}void test(double f) {cout << " The float is " << f << endl;}void test(char const *ch) {cout << " The char* is " << ch << endl;}int main() {test(5);test(5.5);test("five");return 0;}

Producción:

Aquí hay una captura de pantalla del código:

Explicación del código:

  1. Incluya el archivo de encabezado de iostream en nuestro código. Podremos utilizar sus funciones.
  2. Incluya el espacio de nombres estándar en nuestro código. Podremos usar sus clases sin llamarlo.
  3. Cree una función llamada prueba que tome un parámetro entero i. El {marca el comienzo del cuerpo de la prueba de función.
  4. Declaración que se ejecutará si se invoca / llama a la prueba de función anterior.
  5. Fin del cuerpo de la prueba de funcionamiento anterior.
  6. Cree una función llamada prueba que tome un parámetro flotante f. El {marca el comienzo del cuerpo de la prueba de función.
  7. Declaración que se ejecutará si se invoca / llama a la prueba de función anterior.
  8. Fin del cuerpo de la prueba de funcionamiento anterior.
  9. Cree una función llamada prueba que tome un parámetro de carácter ch. El {marca el comienzo del cuerpo de la prueba de función.
  10. Declaración que se ejecutará si se invoca / llama a la prueba de función anterior.
  11. Fin del cuerpo de la prueba de funcionamiento anterior.
  12. Llame a la función main (). {Marca el comienzo del cuerpo de la función.
  13. Llame a la función test y pase 5 como valor del argumento. Esto invoca la función de prueba que acepta un argumento entero, es decir, la primera función de prueba.
  14. Llame a la función test y pasándole 5.5 como valor del argumento. Esto invocará la función de prueba que acepta un argumento flotante, es decir, la segunda función de prueba.
  15. Llame a la función test y pase cinco como valor del argumento. Esto invocará la función de prueba que acepta un argumento de carácter, es decir, la tercera función de prueba.
  16. El programa debe devolver un valor si se ejecuta correctamente.
  17. El final del cuerpo de la función main ().

Tenemos tres funciones con el mismo nombre pero diferentes tipos de argumentos. Hemos logrado el polimorfismo.

Sobrecarga del operador

En Operator Overloading, definimos un nuevo significado para un operador C ++. También cambia la forma en que trabaja el operador. Por ejemplo, podemos definir el operador + para concatenar dos cadenas. Lo conocemos como el operador de suma para sumar valores numéricos. Después de nuestra definición, cuando se coloca entre números enteros, los agregará. Cuando se coloca entre cadenas, las concatenará.

Ejemplo 2:

#includeusing namespace std;class ComplexNum {private:int real, over;public:ComplexNum(int rl = 0, int ov = 0) {real = rl;over = ov;}ComplexNum operator + (ComplexNum const &obj) {ComplexNum result;result.real = real + obj.real;result.over = over + obj.over;return result;}void print() {cout << real << " + i" << over << endl;}};int main(){ComplexNum c1(10, 2), c2(3, 7);ComplexNum c3 = c1+c2;c3.print();}

Producción:

Aquí hay una captura de pantalla del código:

Explicación del código:

  1. Incluya el archivo de encabezado de iostream en nuestro programa para usar sus funciones.
  2. Incluya el espacio de nombres std en nuestro programa para poder usar sus clases sin llamarlo.
  3. Cree una clase llamada ComplexNum. El {marca el comienzo del cuerpo de la clase.
  4. Utilice el modificador de acceso privado para marcar las variables como privadas, lo que significa que solo se puede acceder a ellas desde dentro de la clase.
  5. Defina dos variables enteras, reales y superiores.
  6. Utilice el modificador de acceso público para marcar el constructor como público, lo que significa que será accesible incluso desde fuera de la clase.
  7. Crea el constructor de la clase e inicializa las variables.
  8. Inicializa el valor de la variable real.
  9. Inicializa el valor de la variable sobre.
  10. Fin del cuerpo del constructor.
  11. Necesitamos anular el significado del operador +.
  12. Cree el resultado del tipo de datos de tipo ComplexNum.
  13. Utilice el operador + con números complejos. Esta línea agregará la parte real de un número a la parte real de otro número.
  14. Utilice el operador + con números complejos. Esta línea agregará la parte imaginaria de un número a la parte imaginaria de otro número.
  15. El programa devolverá el valor de la variable resultado después de una ejecución exitosa.
  16. Fin de la definición del nuevo significado de operador +, es decir, sobrecarga.
  17. Llame al método print ().
  18. Imprima el nuevo número complejo después de la adición en la consola.
  19. Fin del cuerpo de la función print ().
  20. Fin del cuerpo de la clase ComplexNum.
  21. Llame a la función main ().
  22. Pase los valores de las partes reales y complejas que se agregarán. La primera parte de c1 se agregará a la primera parte de c2, es decir, 10 + 3. La segunda parte de c1 se agregará a la segunda parte de c, es decir, 2 + 7.
  23. Realice una operación usando el operador + sobrecargado y almacenando el resultado en la variable c3.
  24. Imprime el valor de la variable c3 en la consola.
  25. Fin del cuerpo de la función main ().

Polimorfismo en tiempo de ejecución

Esto sucede cuando se invoca / llama al método de un objeto durante el tiempo de ejecución en lugar de durante el tiempo de compilación. El polimorfismo en tiempo de ejecución se logra mediante la anulación de funciones. La función a llamar / invocar se establece durante el tiempo de ejecución.

Anulación de función

La anulación de función ocurre cuando una función de la clase base recibe una nueva definición en una clase derivada. En ese momento, podemos decir que la función base se ha anulado.

Por ejemplo:

#include using namespace std;class Mammal {public:void eat() {cout << "Mammals eat… ";}};class Cow: public Mammal {public:void eat() {cout << "Cows eat grass… ";}};int main(void) {Cow c = Cow();c.eat();return 0;}

Producción:

Aquí hay una captura de pantalla del código:

Explicación del código:

  1. Importe el archivo de encabezado de iostream a nuestro programa para usar sus funciones.
  2. Incluya el espacio de nombres std en nuestro programa para poder usar sus clases sin llamarlo.
  3. Crea una clase llamada Mamífero. El {marca el comienzo del cuerpo de la clase.
  4. Utilice el modificador de acceso público para establecer la función que estamos a punto de crear como accesible al público. Será accesible desde fuera de esta clase.
  5. Cree una función pública llamada comer. {Marca el comienzo del cuerpo de la función.
  6. Imprime la declaración agregada a la función cout cuando se invoca la función eat ().
  7. El fin del cuerpo de función come ().
  8. Fin del cuerpo de la clase Mamífero.
  9. Cree una clase llamada Vaca que herede la clase Mamífero. Vaca es la clase derivada, mientras que Mamífero es la clase base. El {marca el comienzo de esta clase.
  10. Utilice el modificador de acceso público para marcar la función que estamos a punto de crear como accesible al público. Será accesible desde fuera de esta clase.
  11. Anula la función eat () que se definió en la clase base. {Marca el comienzo del cuerpo de la función.
  12. La declaración que se imprimirá en la consola cuando se invoca esta función.
  13. Fin del cuerpo de la función comer ().
  14. Fin del cuerpo de la clase Vaca.
  15. Llame a la función main (). El {marca el comienzo del cuerpo de esta función.
  16. Cree una instancia de la clase Cow y asígnele el nombre c.
  17. Llame a la función eat () definida en la clase Cow.
  18. El programa debe devolver un valor una vez completado con éxito.
  19. Fin de la función main ().

Función virtual C ++

Una función virtual es otra forma de implementar el polimorfismo en tiempo de ejecución en C ++. Es una función especial definida en una clase base y redefinida en la clase derivada. Para declarar una función virtual, debe usar la palabra clave virtual. La palabra clave debe preceder a la declaración de la función en la clase base.

Si se hereda una clase de función virtual, la clase virtual redefine la función virtual para satisfacer sus necesidades. Por ejemplo:

#include using namespace std;class ClassA {public:virtual void show() {cout << "The show() function in base class invoked… " << endl;}};class ClassB :public ClassA {public:void show() {cout << "The show() function in derived class invoked… ";}};int main() {ClassA* a;ClassB b;a = &b;a->show();}

Producción:

Aquí hay una captura de pantalla del código:

Explicación del código:

  1. Incluya el archivo de encabezado de iostream en el código para usar sus funciones.
  2. Incluya el espacio de nombres std en nuestro código para usar sus clases sin llamarlo.
  3. Cree una clase llamada ClassA.
  4. Utilice el modificador de acceso público para marcar un miembro de la clase como accesible al público.
  5. Cree una función virtual llamada show (). Será una función pública.
  6. El texto que se imprimirá cuando se invoca show (). Endl es una palabra clave de C ++, que significa línea final. Mueve el cursor del mouse a la siguiente línea.
  7. Fin del cuerpo de la función virtual show ().
  8. Fin del cuerpo de la clase ClassA.
  9. Creando una nueva clase llamada ClassB que hereda la clase ClassA. ClassA se convierte en la clase base mientras que ClassB se convierte en la clase derivada.
  10. Utilice el modificador de acceso público para marcar un miembro de la clase como accesible al público.
  11. Redefina la función virtual show () derivada en la clase base.
  12. El texto que se imprimirá en la consola cuando se invoca la función show () definida en la clase derivada.
  13. Fin del cuerpo de la función show ().
  14. Fin del cuerpo de la clase derivada, ClassB.
  15. Llame a la función main (). La lógica del programa debe agregarse dentro de su cuerpo.
  16. Cree una variable de puntero denominada a. Apunta a la clase denominada ClassA.
  17. Cree una instancia de la clase denominada ClassB. La instancia recibe el nombre b.
  18. Asignar los valores almacenados en la dirección b en la variable a.
  19. Invoque la función show () definida en la clase derivada. Se ha implementado la vinculación tardía.
  20. Fin del cuerpo de la función main ().

Polimorfismo en tiempo de compilación vs. Polimorfismo en tiempo de ejecución

Aquí están las principales diferencias entre los dos:

Polimorfismo en tiempo de compilación Polimorfismo en tiempo de ejecución
También se llama polimorfismo estático o de unión temprana. También se denomina enlace tardío / dinámico o polimorfismo dinámico.
El método se llama / invoca durante el tiempo de compilación El método se llama / invoca durante el tiempo de ejecución
Implementado mediante sobrecarga de funciones y sobrecarga del operador Implementado a través de funciones virtuales y anulación de métodos
Ejemplo, sobrecarga de métodos. Muchos métodos pueden tener nombres similares pero diferentes números o tipos de argumentos Ejemplo, anulación de método. Muchos métodos pueden tener un nombre similar y el mismo prototipo.
Ejecución más rápida ya que el descubrimiento de métodos se realiza durante el tiempo de compilación Ejecución más lenta ya que el descubrimiento de métodos se realiza durante el tiempo de ejecución.
Se proporciona menos flexibilidad para la resolución de problemas, ya que todo se conoce durante el tiempo de compilación. Se proporciona mucha flexibilidad para resolver problemas complejos, ya que los métodos se descubren durante el tiempo de ejecución.

Resumen:

  • Polimorfismo significa tener muchas formas.
  • Ocurre cuando existe una jerarquía de clases relacionadas por herencia.
  • Con el polimorfismo, una función puede comportarse de manera diferente según el objeto que la invoca / llama.
  • En el polimorfismo en tiempo de compilación, la función que se invocará se establece durante el tiempo de compilación.
  • En el polimorfismo en tiempo de ejecución, la función que se va a invocar se establece durante el tiempo de ejecución.
  • El polimorfismo en tiempo de compilación se determina mediante la sobrecarga de funciones y la sobrecarga de operadores.
  • En la sobrecarga de funciones, hay muchas funciones con nombres similares pero argumentos diferentes.
  • Los parámetros pueden diferir en número o tipo.
  • En la sobrecarga de operadores, se define un nuevo significado para los operadores de C ++.
  • El polimorfismo en tiempo de ejecución se logra mediante la anulación de funciones.
  • En la sustitución de funciones, una clase derivada da una nueva definición a una función definida en la clase base.