How to Sort a List of Complex Type in C#

How to Sort a List of Complex Types in C#

In this article, I am going to discuss How to Sort a List of Complex Types in C# like Employee, Customer, Product, Department, etc. with examples. Please read our previous article where we discussed Generic List in C# with Examples. Before understanding, how to sort a complex type, let us first understand how to sort simple types like int, double, char, string, etc.

List<T> Class Sort Method in C#:

The Generic List Collection Class in C# provides the following four Sort Methods.

  1. Sort(): This method is used to sort the elements in the entire Generic List using the default comparer.
  2. Sort(IComparer<T>? comparer): This method is used to sort the elements in the entire Generic List using the specified comparer.
  3. Sort(Comparison<T> comparison): This method is used to sort the elements in the entire Generic List using the specified System.Comparison.
  4. Sort(int index, int count, IComparer<T>? comparer): This method is used to sort the elements in a range of elements in a Generic List using the specified comparer.
How to Sort a List of Simple Types in C#:

Sorting a generic list collection of simple types is very straightforward. We just need to invoke the Sort() method (Provided by the Generic List class) on the list instance and the data will be automatically sorted in ascending order. For example, if we have a list of integers as shown below
List<int> numbersList = new List<int>{ 1, 8, 7, 5, 2 };
Then we just need to invoke the Sort() method on numbersList collection as shown below
numbersList.Sort();

Example showing a List Collection of Simple Types in C#:

In the below example, we are creating list collections of int and string types and then calling the Sort Method to Sort the collection and the Reverse Method to reverse the collection.

using System;
using System.Collections.Generic;

namespace ListCollectionSortReverseMethodDemo
{
    public class Program
    {
        public static void Main()
        {
            List<int> numbersList = new List<int> { 1, 8, 7, 5, 2 };
            Console.WriteLine("Numbers Before Sorting");
            foreach (int i in numbersList)
            {
                Console.Write($"{i} ");
            }

            // The Sort() of List Collection class will sort the data in ascending order 
            numbersList.Sort();
            Console.WriteLine("\n\nNumbers After Sorting");
            foreach (int i in numbersList)
            {
                Console.Write($"{i} ");
            }

            // If you want to  to retrieve data in descending order then use the Reverse() method
            numbersList.Reverse();
            Console.WriteLine("\n\nNumbers in Descending order");
            foreach (int i in numbersList)
            {
                Console.Write($"{i} ");
            }

            //Another Example of Sorting String
            List<string> names = new List<string>() { "Pranaya", "Anurag", "Sambit", "Hina", "Rakesh" };
            Console.WriteLine("\n\nNames Before Sorting");
            foreach (string name in names)
            {
                Console.WriteLine(name);
            }

            names.Sort();
            Console.WriteLine("\nNames After Sorting");
            foreach (string name in names)
            {
                Console.WriteLine(name);
            }

            names.Reverse();
            Console.WriteLine("\nNames in Descending Order");
            foreach (string name in names)
            {
                Console.WriteLine(name);
            }

            Console.ReadKey();
        }
    }
}
Output:

Example showing a List Collection of Simple Types in C#

However, when we do the same thing on a complex type like Employee, Product, Customer, Department, etc. we will get a runtime exception as “invalid operation exception – Failed to compare 2 elements in the array”. This is because at runtime the .NET Framework does not identify how to sort the complex types. So, if we want to sort a complex type then we need to tell the way we want the data to be sorted in the list, and to do this we need to implement the IComparable interface. We will discuss this in our next article.

How the sort functionality is working for simple data types like int, double, string, char, etc. in C#?

This is working because these types (int, double, string, decimal, char, etc.) are already implementing the IComparable interface. If you go to the definition of any built-in types, then you will see that the class is implemented IComparable interface. For example, if you go to the definition of int and string, then you will see that they implement the IComparable interface as shown in the below image.

How the sort functionality is working for simple data types like int, double, string, char, etc. in C#

Sorting a List Collection of Complex Type in C#

In the following example, we are creating a collection of Employee Types and then trying to Sort the Employees by calling the Sort method on the listEmployees instance. Here, we will not get any compile-time error. But the Invoking Sort() on a list of complex types will throw runtime exception i.e. Invalid Operation Exception unless we implement the IComparable interface.

using System;
using System.Collections.Generic;
namespace ListCollectionSortReverseMethodDemo
{
    public class Program
    {
        public static void Main()
        {
            Employee emp1 = new Employee()
            {
                ID = 101,
                Name = "Pranaya",
                Gender = "Male",
                Salary = 5000
            };
            Employee emp2 = new Employee()
            {
                ID = 102,
                Name = "Priyanka",
                Gender = "Female",
                Salary = 7000
            };
            Employee emp3 = new Employee()
            {
                ID = 103,
                Name = "Anurag",
                Gender = "Male",
                Salary = 4500
            };
            Employee emp4 = new Employee()
            {
                ID = 104,
                Name = "Sambit",
                Gender = "Male",
                Salary = 6500
            };
            Employee emp5 = new Employee()
            {
                ID = 105,
                Name = "Hina",
                Gender = "Female",
                Salary = 7500
            };
            Employee emp6 = new Employee()
            {
                ID = 106,
                Name = "Tarun",
                Gender = "Male",
                Salary = 6000
            };
            List<Employee> listEmployees = new List<Employee>();
            listEmployees.Add(emp1);
            listEmployees.Add(emp2);
            listEmployees.Add(emp3);
            listEmployees.Add(emp4);
            listEmployees.Add(emp5);
            listEmployees.Add(emp6);
            Console.WriteLine("Employees before sorting");
            foreach (Employee employee in listEmployees)
            {
                Console.WriteLine("ID = {0}, Name = {1},  Gender = {2}, Salary = {3}",
                    employee.ID, employee.Name, employee.Gender, employee.Salary);
            }
            
            listEmployees.Sort();
            Console.WriteLine("Employees After sorting");
            foreach (Employee employee in listEmployees)
            {
                Console.WriteLine("ID = {0}, Name = {1},  Gender = {2}, Salary = {3}",
                    employee.ID, employee.Name, employee.Gender, employee.Salary);
            }
            Console.ReadKey();
        }
    }
    public class Employee
    {
        public int ID { get; set; }
        public string Name { get; set; }
        public string Gender { get; set; }
        public int Salary { get; set; }
    }
}

When we execute the above code, it will give us the below runtime exception.

How to Sort a List of Complex Type in C#

To sort a list of complex type without using LINQ, the complex type has to implement the IComparable interface and needs to provide the implementation for the CompareTo() method as follows. The CompareTo() method returns an integer value and the meaning of the return value as shown below.

  1. Return value greater than ZERO – The current instance is greater than the object being compared with.
  2. Return value less than ZERO – The current instance is less than the object being compared with.
  3. The Return value is ZERO – The current instance is equal to the object being compared with.

Alternatively, we can also invoke the CompareTo() method directly. The Salary property of the Employee object is int and the CompareTo() method is already implemented on the integer type that we already discussed, so we can invoke this method and return its value as shown below.
return this.Salary.CompareTo(obj.Salary);

Implementing the IComparable interface in C# in Employee Class

Let’s understand this with an example. What we want is, we need to sort the employees based on their Salary. To do so, our Employee class should implement the IComparable interface and should provide an implementation for the CompareTo() method. This method will compare the current object (specified with this) and the object to be compared which it will get as a parameter. So. modify the Employee class as follows and the following code exactly does the same.

public class Employee : IComparable<Employee>
{
    public int ID { get; set; }
    public string Name { get; set; }
    public string Gender { get; set; }
    public int Salary { get; set; }
    public int CompareTo(Employee obj)
    {
        if (this.Salary > obj.Salary)
        {
            return 1;
        }
        else if (this.Salary < obj.Salary)
        {
            return -1;
        }
        else
        {
            return 0;
        }
    }
}

Now run the application. It will give you the result in ascending order based on the Employee Salary as shown in the below image.

How to Sort a List of Complex Type in C#

If you prefer not to use the Sort functionality provided by the Employee class, then you can provide your own implementation by implementing the IComparer interface. For example, if you want the employees to be sorted by Name instead of Salary then you need to follow the below two steps.

Step1: Implement the IComparer interface

public class SortByName : IComparer<Employee>
{
    public int Compare(Employee x, Employee y)
    {
        return x.Name.CompareTo(y.Name);
    }
}

Step2: Pass an instance of the class that implements the IComparer interface as an argument to the Sort() method as shown below.

SortByName sortByName = new SortByName();
listEmployees.Sort(sortByName);

Complete Example to use own Comparer to Sort Employee by Name:
using System;
using System.Collections.Generic;
namespace ListCollectionSortReverseMethodDemo
{
    public class Program
    {
        public static void Main()
        {
            Employee emp1 = new Employee()
            {
                ID = 101,
                Name = "Pranaya",
                Gender = "Male",
                Salary = 5000
            };
            Employee emp2 = new Employee()
            {
                ID = 102,
                Name = "Priyanka",
                Gender = "Female",
                Salary = 7000
            };
            Employee emp3 = new Employee()
            {
                ID = 103,
                Name = "Anurag",
                Gender = "Male",
                Salary = 4500
            };
            Employee emp4 = new Employee()
            {
                ID = 104,
                Name = "Sambit",
                Gender = "Male",
                Salary = 6500
            };
            Employee emp5 = new Employee()
            {
                ID = 105,
                Name = "Hina",
                Gender = "Female",
                Salary = 7500
            };
            Employee emp6 = new Employee()
            {
                ID = 106,
                Name = "Tarun",
                Gender = "Male",
                Salary = 6000
            };
            List<Employee> listEmployees = new List<Employee>();
            listEmployees.Add(emp1);
            listEmployees.Add(emp2);
            listEmployees.Add(emp3);
            listEmployees.Add(emp4);
            listEmployees.Add(emp5);
            listEmployees.Add(emp6);
            Console.WriteLine("Employees before sorting");
            foreach (Employee employee in listEmployees)
            {
                Console.WriteLine("ID = {0}, Name = {1},  Gender = {2}, Salary = {3}",
                    employee.ID, employee.Name, employee.Gender, employee.Salary);
            }
            SortByName sortByName = new SortByName();
            listEmployees.Sort(sortByName);
            Console.WriteLine("Employees After sorting");
            foreach (Employee employee in listEmployees)
            {
                Console.WriteLine("ID = {0}, Name = {1},  Gender = {2}, Salary = {3}",
                    employee.ID, employee.Name, employee.Gender, employee.Salary);
            }
            Console.ReadKey();
        }
    }
    public class SortByName : IComparer<Employee>
    {
        public int Compare(Employee x, Employee y)
        {
            return x.Name.CompareTo(y.Name);
        }
    }
    public class Employee
    {
        public int ID { get; set; }
        public string Name { get; set; }
        public string Gender { get; set; }
        public int Salary { get; set; }
    }
}

Now run the application and should give the following output.

How to Sort a List of Complex Type in C#

In the next article, I am going to discuss the Comparison Delegate in C# with Examples. Here, in this article, I try to explain How to Sort a List of Complex Type in C# with Examples. I hope this How to Sort a List of Complex Type in C# with Examples article will help you with your needs. I would like to have your feedback. Please post your feedback, question, or comments about this article.

6 thoughts on “How to Sort a List of Complex Type in C#”

    1. blank

      Not sure If I did it properly…


      using System.Collections.Generic;
      using static System.Console;

      namespace UnderstandingListSorting
      {
      public class Program
      {
      public static void Main()
      {
      List listEmployees = new List()
      {
      new Employee() {ID = 101, Name = "Pranaya", Gender = "Male", Salary = 5000},
      new Employee() {ID = 102, Name = "Priyanka", Gender = "Female", Salary = 7000},
      new Employee() {ID = 103, Name = "Anurag", Gender = "Male", Salary = 4500},
      new Employee() {ID = 104, Name = "Sambit", Gender = "Male", Salary = 6500},
      new Employee() {ID = 105, Name = "Hina", Gender = "Female", Salary = 7500},
      new Employee() {ID = 106, Name = "Tarun", Gender = "Male", Salary = 6000}
      };

      WriteLine("Employees before sorting");
      foreach (Employee employee in listEmployees)
      {
      WriteLine($"ID = {employee.ID}, Name = {employee.Name}, Gender = {employee.Gender}, Salary = {employee.Salary}");
      }

      SortBySalary sortBySalary = new SortBySalary();
      listEmployees.Sort(sortBySalary);

      WriteLine("Employees after sorting - by salary");
      foreach (Employee employee in listEmployees)
      {
      WriteLine($"ID = {employee.ID}, Name = {employee.Name}, Gender = {employee.Gender}, Salary = {employee.Salary}");
      }

      SortByName sortByName = new SortByName();
      listEmployees.Sort(sortByName);

      WriteLine("Employees after sorting - by name");
      foreach (Employee employee in listEmployees)
      {
      WriteLine($"ID = {employee.ID}, Name = {employee.Name}, Gender = {employee.Gender}, Salary = {employee.Salary}");
      }

      ReadKey();
      }
      }
      public class Employee
      {
      public int ID { get; set; }
      public string Name { get; set; }
      public string Gender { get; set; }
      public int Salary { get; set; }
      }
      public class SortBySalary : IComparer
      {
      int IComparer.Compare(Employee x, Employee y)
      {
      if (x.Salary.CompareTo(y.Salary) != 0)
      {
      return x.Salary.CompareTo(y.Salary);
      }
      else
      {
      return 0;
      }
      }
      }
      public class SortByName : IComparer
      {
      int IComparer.Compare(Employee x, Employee y)
      {
      if (x.Name.CompareTo(y.Name) != 0)
      {
      return x.Name.CompareTo(y.Name);
      }
      else
      {
      return 0;
      }
      }
      }
      }

  1. blank
    Loknadh.Ravineni

    I have tried the below code worked for me !!!!

    static void Main(string[] args)
    {
    Employee emp1 = new Employee()
    {
    ID = 101,
    Name = “Pranaya”,
    Gender = “Male”,
    Salary = 5000
    };
    Employee emp2 = new Employee()
    {
    ID = 102,
    Name = “Priyanka”,
    Gender = “Female”,
    Salary = 7000
    };
    Employee emp3 = new Employee()
    {
    ID = 103,
    Name = “Anurag”,
    Gender = “Male”,
    Salary = 5500
    };
    Employee emp4 = new Employee()
    {
    ID = 104,
    Name = “Sambit”,
    Gender = “Male”,
    Salary = 6500
    };
    Employee emp5 = new Employee()
    {
    ID = 105,
    Name = “Hina”,
    Gender = “Female”,
    Salary = 7500
    };
    Employee emp6 = new Employee()
    {
    ID = 106,
    Name = “Tarun”,
    Gender = “Male”,
    Salary = 8500
    };
    List firstlist = new List();
    Console.WriteLine(“Using Add method to add the data to the list”);
    Console.WriteLine();
    firstlist.Add(emp1);
    firstlist.Add(emp2);
    firstlist.Add(emp3);

    foreach (var item in firstlist)
    {
    Console.WriteLine($”Id:{item.ID}, Name:{item.Name}, Gender:{item.Gender}, Salary:{item.Salary}”);
    }
    Console.WriteLine();
    Console.WriteLine(“items present in the list before sorting list”);
    Console.WriteLine();
    firstlist.Sort();

    Console.WriteLine(“The elements of the list is after Sorting is “);

    foreach (var item2 in firstlist)
    {
    Console.WriteLine($”Id:{item2.ID}, Name:{item2.Name}, Gender:{item2.Gender}, Salary:{item2.Salary}”);
    }

    Console.ReadLine();

    }

    public class Employee:IComparable
    {
    public int ID { get; set; }
    public string Name { get; set; }
    public string Gender { get; set; }
    public int Salary { get; set; }

    public int CompareTo(Employee other)
    {
    return this.ID.CompareTo(other.ID);
    }
    }

Leave a Reply

Your email address will not be published.