Blog for Junior Developers C#/.NET

Friday, July 12, 2024

Today it's time for another very important topic in object-oriented programming that every person who wants to become a junior .NET developer must understand. From the article you will learn what polymorphism is in object-oriented programming, of course I will try to explain it to you with examples in C#. Polymorphism is very related to inheritance, so if you don't know what inheritance is yet, it's best to go back to the previous blog article, that is: Inheritance in object-oriented programming.

what-is-polymorphism-in-object-oriented-programming.jpg

What is polymorphism?


Polymorphism (multiformity) is one of the basic assumptions of object-oriented programming. Multiform, i.e. writing one function (method) in different forms. That is, with it we can handle different types in different ways without knowing those types. Polymorphism can be divided into 2 groups, static polymorphism and dynamic polymorphism.


Static polymorphism


In C#, this means overloading functions and operators. The point is that in 1 class there may be many methods with the same name, but differing only in parameters. Static polymorphism occurs during program compilation, which method is selected depends on the number and type of arguments passed to the method. It's worth mentioning that you can't overload a method that only differs in return type.


Dynamic polymorphism


in C# is associated with virtual and abstract functions, this is called function overriding. The idea of ​​(dynamic) polymorphism revolves around class inheritance. To override a method in a base class, use the virtual keyword and in a subclass, use the override keyword. Usually, when someone talks about polymorphism, they mean dynamic polymorphism. The examples in this article will also concern dynamic polymorphism.


C# task


In the last article, I described what inheritance is. Polymorphism (dynamic) is closely related to inheritance. Take a look at the example below, which shows the inheritance hierarchy of several classes.

public class Shape
{
        
}

public class Square : Shape
{

}

public class Triangle : Shape
{

}

public class Program
{
    static void Main(string[] args)
    {
        var shapes = new List<Shape>()
        {
            new Square(),
            new Triangle()
        };
    }
}


Here we have the Shape class, from which the Square and Triangle classes inherit. Let's assume that we have to write a program that will draw various shapes of figures that will be in the given shapes list.


Bad solution (no polymorphism)


First, let's start with the bad solution, i.e. what such a program could look like without the use of polymorphism.

public class Shape
{
        
}

public class Square : Shape
{
    public void DrawSquare()
    {
        Console.WriteLine("Draw Square");
    }
}

public class Triangle : Shape
{
    public void DrawTriangle()
    {
        Console.WriteLine("Draw Triangle");
    }
}


public class Program
{
    static void Main(string[] args)
    {
        var shapes = new List<Shape>()
        {
            new Square(),
            new Triangle()
        };

        foreach (var shape in shapes)
        {
            if (shape is Square)
                (shape as Square).DrawSquare();
            else if (shape is Triangle)
                (shape as Triangle).DrawTriangle();
        }
    }
}

//OUTPUT
//Draw Square
//Draw Triangle


Although the result is correct and does what we need, this solution is very problematic and creates a big mess in the code. If in the future we need to add a new figure that we also want to draw, the Main method will have to be modified and further conditions will be needed to check what type the object is.


Correct solution using polymorphism


So how should these classes be properly designed? You should use polymorphism.

public class Shape
{
    public virtual void Draw()
    {
    }
}

public class Square : Shape
{
    public override void Draw()
    {
        Console.WriteLine("Draw Square");
    }
}

public class Triangle : Shape
{
    public override void Draw()
    {
        Console.WriteLine("Draw Triangle");
    }
}


public class Program
{
    static void Main(string[] args)
    {
        var shapes = new List<Shape>()
        {
            new Square(),
            new Triangle()
        };

        foreach (var shape in shapes)
        {
             shape.Draw();
        }
    }
}

//OUTPUT
//Draw Square
//Draw Triangle


In the above example we used polymorphism. As you can see, this time in the Main method we no longer need to check the type of the object. If a new class is added to our application, the Main method will not have to be changed either. And now I will try to explain to you what we have changed. First of all, we added a new Draw method to the Shape class. As you can see, it is a virtual method, i.e. marked with the virtual keyword. When we mark a method as virtual, we allow this method to be overwritten by a subordinate (inheriting) class. To overwrite such a method in a subclass, we must use the override keyword, thanks to which we overwrite a method with the same definition with our own implementation. Thanks to this, the Square and Triangle classes have their own overwritten implementation of the Draw method. Therefore, in the Main method, when iterating through the Shapes list, the expected implementation is called each time without type checking. Polymorphism is still closely related to abstract classes and methods, so I will cover this topic in the next article.


SUMMARY:


Polymorphism is a very important pillar of object-oriented programming, without knowledge of which it will be difficult to find a job as a junior C#/.NET programmer. I showed you how polymorphism is divided and what its applications are. The most important thing is to remember the keywords virtual (to designate methods that can be overridden in a derived class) and override (to designate overridden methods). If you have any questions about this article, please write me an e-mail or leave a comment. Next week we will discuss the topic of abstraction in object-oriented programming, and then I will also expand on the topic of polymorphism.

Author of the article:
Kazimierz Szpin

KAZIMIERZ SZPIN
Software Developer C#/.NET, Freelancer. Specializes in ASP.NET Core, ASP.NET MVC, ASP.NET Web API, Blazor, WPF and Windows Forms.
Author of the blog CodeWithKazik.com

Previous article - What is Inheritance in Object Oriented Programming?
Next article - What is Abstraction in Object Oriented Programming?
Comments (1)
Kazimierz Szpin
KAZIMIERZ SZPIN, poniedziałek, 15 lipca 2024 11:03
What do you think about this article? I'm curious about your opinion.
Dodaj komentarz
© Copyright 2024 CodeWithKazik.com. All rights reserved. Privacy policy.
Design by Code With Kazik and Modest Programmer.