C # - Polimorfismo

La palabra polymorphismsignifica tener muchas formas. En el paradigma de la programación orientada a objetos, el polimorfismo a menudo se expresa como "una interfaz, múltiples funciones".

El polimorfismo puede ser estático o dinámico. Enstatic polymorphism, la respuesta a una función se determina en el momento de la compilación. Endynamic polymorphism, se decide en tiempo de ejecución.

Polimorfismo estático

El mecanismo de vincular una función con un objeto durante el tiempo de compilación se denomina vinculación anticipada. También se llama enlace estático. C # proporciona dos técnicas para implementar el polimorfismo estático. Ellos son -

  • Sobrecarga de funciones
  • Sobrecarga del operador

Analizamos la sobrecarga del operador en el próximo capítulo.

Sobrecarga de funciones

Puede tener varias definiciones para el mismo nombre de función en el mismo ámbito. La definición de la función debe diferir entre sí por los tipos y / o el número de argumentos en la lista de argumentos. No puede sobrecargar declaraciones de funciones que difieran solo por el tipo de retorno.

El siguiente ejemplo muestra el uso de la función print() para imprimir diferentes tipos de datos -

using System;

namespace PolymorphismApplication {
   class Printdata {
      void print(int i) {
         Console.WriteLine("Printing int: {0}", i );
      }
      void print(double f) {
         Console.WriteLine("Printing float: {0}" , f);
      }
      void print(string s) {
         Console.WriteLine("Printing string: {0}", s);
      }
      static void Main(string[] args) {
         Printdata p = new Printdata();
         
         // Call print to print integer
         p.print(5);
         
         // Call print to print float
         p.print(500.263);
         
         // Call print to print string
         p.print("Hello C++");
         Console.ReadKey();
      }
   }
}

Cuando se compila y ejecuta el código anterior, produce el siguiente resultado:

Printing int: 5
Printing float: 500.263
Printing string: Hello C++

Polimorfismo dinámico

C # le permite crear clases abstractas que se utilizan para proporcionar una implementación de clase parcial de una interfaz. La implementación se completa cuando una clase derivada hereda de ella.Abstractlas clases contienen métodos abstractos, que son implementados por la clase derivada. Las clases derivadas tienen una funcionalidad más especializada.

Aquí están las reglas sobre las clases abstractas:

  • No puedes crear una instancia de una clase abstracta

  • No puede declarar un método abstracto fuera de una clase abstracta

  • Cuando se declara una clase sealed, no se puede heredar, las clases abstractas no se pueden declarar selladas.

El siguiente programa demuestra una clase abstracta:

using System;

namespace PolymorphismApplication {
   abstract class Shape {
      public abstract int area();
   }
   
   class Rectangle:  Shape {
      private int length;
      private int width;
      
      public Rectangle( int a = 0, int b = 0) {
         length = a;
         width = b;
      }
      public override int area () { 
         Console.WriteLine("Rectangle class area :");
         return (width * length); 
      }
   }
   class RectangleTester {
      static void Main(string[] args) {
         Rectangle r = new Rectangle(10, 7);
         double a = r.area();
         Console.WriteLine("Area: {0}",a);
         Console.ReadKey();
      }
   }
}

Cuando se compila y ejecuta el código anterior, produce el siguiente resultado:

Rectangle class area :
Area: 70

Cuando tiene una función definida en una clase que desea implementar en una (s) clase (s) heredada, usa virtualfunciones. Las funciones virtuales podrían implementarse de manera diferente en diferentes clases heredadas y la llamada a estas funciones se decidirá en tiempo de ejecución.

El polimorfismo dinámico se implementa mediante abstract classes y virtual functions.

El siguiente programa demuestra esto:

using System;

namespace PolymorphismApplication {
   class Shape {
      protected int width, height;
      
      public Shape( int a = 0, int b = 0) {
         width = a;
         height = b;
      }
      public virtual int area() {
         Console.WriteLine("Parent class area :");
         return 0;
      }
   }
   class Rectangle: Shape {
      public Rectangle( int a = 0, int b = 0): base(a, b) {

      }
      public override int area () {
         Console.WriteLine("Rectangle class area :");
         return (width * height); 
      }
   }
   class Triangle: Shape {
      public Triangle(int a = 0, int b = 0): base(a, b) {
      }
      public override int area() {
         Console.WriteLine("Triangle class area :");
         return (width * height / 2); 
      }
   }
   class Caller {
      public void CallArea(Shape sh) {
         int a;
         a = sh.area();
         Console.WriteLine("Area: {0}", a);
      }
   }  
   class Tester {
      static void Main(string[] args) {
         Caller c = new Caller();
         Rectangle r = new Rectangle(10, 7);
         Triangle t = new Triangle(10, 5);
         
         c.CallArea(r);
         c.CallArea(t);
         Console.ReadKey();
      }
   }
}

Cuando se compila y ejecuta el código anterior, produce el siguiente resultado:

Rectangle class area:
Area: 70
Triangle class area:
Area: 25