Polymorphism in Java

Polymorphism in Java

This article covers polymorphism in Java, an important OOP principle.

The word Polymorphism is a combination of two Greek words: Poly which means many and Morph which means forms.

What if we want our derived class to inherit a method from the base class and have a different implementation for it? That is when polymorphism comes into play.

Let's look at an example of the Shape class, which is the base class while many shapes like Rectangle and Circle extending from the base class are derived classes. These classes contain the getPerimeter() method which calculates the perimeter for the respective shape. Each of the derived shapes can have its own implementation of the method.

// A simple Shape which provides a method to get the Shape's perimeter
class Shape {
  // Method to be overriden
  public double getPerimeter() {
    return 0;
  }
}

// A Circle is a Shape with a specific radius
class Circle extends Shape {
  private double radius; // Private field

  public Circle(double radius) { // Parameterized constructor
    this.radius = radius;
  }
  @Override
  public double getPerimeter() { //Public overridng method to calculate perimeter
    return 2 * Math.PI * radius;
  }
}

// A Recangle is a Shape with a specific length and width
class Rectangle extends Shape {
  // Private fields
  private double width;
  private double height;

  public Rectangle(double width, double height) { // Parameterized constructor
    this.width = width;
    this.height = height;
  }
  @Override
  public double getPerimeter() { //Public overriding method to calculate perimeter
    return 2 * (width + height);
  }
}

public class Main {
  public static void main(String[] args) {
    Shape myShape = new Shape();  // Create new shape
    Circle myCircle = new Circle(5);  // Create new circle
    Rectangle myRectangle = new Rectangle(3, 4);  //Create new rectangle

    System.out.println("Perimeter of shape: " + myShape.getPerimeter());
    System.out.println("Perimeter of circle: " + myCircle.getPerimeter());
    System.out.println("Perimeter of rectangle: " + myRectangle.getPerimeter());
  }
}

Polymorphism cuts down the work we do because when we have to create subclasses with unique attributes and behaviors, we can alter the code in the particular portions where the responses differ. All other code can be left untouched.

In the code above, we have mentioned method overriding. Method overriding is the process of redefining a parent class’s method in a subclass.

  • The method in the parent class is called overridden method.

  • The methods in the child classes are called overriding methods.

In order for method overriding to occur, the following conditions must be met:

  1. The method in the subclass must have the same name, parameter types, access modifier, and return type as the method in the parent class.

  2. The method in the subclass must be declared with the @Override annotation.

  3. The method in the parent class must not be declared as final.

  4. Method overriding needs inheritance and there should be at least one derived class.

  5. The method in the derived class(es) must have different implementations from each other.

  6. The method in the base class must be overridden in the derived class.

Difference between method overloading and method overriding

When we covered methods, we talked about method overloading. At this point, it's important we go through the differences between method overloading and method overriding.

Method OverloadingMethod Overriding
Method overloading is a feature in object-oriented programming (OOP) that allows a class to have multiple methods with the same name, but different argument types.Method overriding is a feature in object-oriented programming (OOP) that allows a subclass to provide a specific implementation of a method that is already provided by one of its parent classes.
Method overloading is done at compile time.Method overriding is done at runtime.
Method overloading gives better performance because the binding is being done at compile time.Method overriding gives less performance because the binding is being done at run time.
Private and final methods can be overloaded.Private and final methods cannot be overridden.
The return type of a method does not matter in the case of method overloading.The return type of a method must be the same in the case of overriding.
The arguments of a method must be different in the case of method overloading.The arguments of a method must be the same in the case of overriding.
Method overloading can be done in the same class.Method overriding requires a base and derived class.
Method overloading is mostly used to increase the readability of the code.Method overriding is mostly used to provide a specific implementation of a method that is already provided by one of its parent classes.
Also known as static or compile-time polymorphismAlso known as dynamic or run-time polymorphism.

With this, we have adequately covered polymorphism and the key differences between static and dynamic polymorphism including when to implement the two. Happy coding! 😁