The Wayback Machine - https://web.archive.org/web/20250306132650/https://www.geeksforgeeks.org/comparator-interface-java/
Open In App

Java Comparator Interface

Last Updated : 13 Jan, 2025
Summarize
Comments
Improve
Suggest changes
Like Article
Like
Share
Report
News Follow

Comparator interface in Java is used to order the objects of user-defined classes. A comparator object is capable of comparing two objects of the same class. Following function compare obj1 with obj2.

Syntax: 

public int compare(Object obj1, Object obj2):

Suppose we have an Array/ArrayList of our own class type, containing fields like roll no, name, address, DOB, etc, and we need to sort the array based on Roll no or name?

Methods to Implement Comparator Interface

  • Method 1: One obvious approach is to write our own sort() function using one of the standard algorithms. This solution requires rewriting the whole sorting code for different criteria like Roll No. and Name.
  • Method 2: Using comparator interface – Comparator interface is used to order the objects of a user-defined class. This interface is present in java.util package and contains 2 methods compare(Object obj1, Object obj2) and equals(Object element). Using a comparator, we can sort the elements based on data members. For instance, it may be on roll no, name, age, or anything else.

How do the sort() method of Collections class work? 

Method of Collections class for sorting List elements is used to sort the elements of List by the given comparator.  

public void sort(List list, ComparatorClass c)

To sort a given List, ComparatorClass must implement a Comparator interface.

Internally the Sort method does call Compare method of the classes it is sorting. To compare two elements, it asks “Which is greater?” Compare method returns -1, 0, or 1 to say if it is less than, equal, or greater to the other. It uses this result to then determine if they should be swapped for their sort.

Example:

Java
// Using Comparator Interface
import java.util.*;

// Define the Student class
class Student {
    int rollno;
    String name;

      // Constructor
    Student(int rollno, String name) {
        this.rollno = rollno;
        this.name = name;
    }

      // Method to print Student
      // details in main()
    @Override
    public String toString() {
        return rollno + ": " + name;
    }
}

// Helper class implementing Comparator interface
class SortbyRoll implements Comparator<Student> 
{    
      // Compare by roll number in ascending order
    public int compare(Student a, Student b) {
        return a.rollno - b.rollno;
    }
}

// Driver Class
public class GFG
{
    public static void main(String[] args) 
    {
          // List of Students
        List<Student> students = new ArrayList<>();
        
          // Add Elements in List
          students.add(new Student(111, "Mayank"));
        students.add(new Student(131, "Anshul"));
        students.add(new Student(121, "Solanki"));
        students.add(new Student(101, "Aggarwal"));

        // Sort students by roll number
          // using SortbyRoll comparator
        Collections.sort(students, new SortbyRoll());

          System.out.println("Sorted by Roll Number ");

        // Iterating over entries to print them
        for (int i = 0; i < students.size(); i++)
            System.out.println(students.get(i));
          
    }
}

Output
Sorted by Roll Number 
101: Aggarwal
111: Mayank
121: Solanki
131: Anshul

By changing the return value inside the compare method, you can sort in any order that you wish to, for example: For descending order just change the positions of ‘a’ and ‘b’ in the above compare method.

Note: we can use lambda expression in place of helper function by following the statement as mentioned below:

students.sort((p1, p2) -> Integer.compare(p1.age, p2.age));

Sort Collection by more than one field

In the previous example, we have discussed how to sort the list of objects on the basis of a single field using the Comparable and Comparator interface But, what if we have a requirement to sort ArrayList objects in accordance with more than one field like firstly, sort according to the student name and secondly, sort according to student age.

Example

Java
// Using Comparator Interface Via 
// More than One Field
import java.util.*;

// Define the Student class
class Student 
{
    String name;
    Integer age;

      // Constructor
    Student(String name, Integer age) {
        this.name = name;
        this.age = age;
    }

    public String getName() {
        return name;
    }

    public Integer getAge() {
        return age;
    }

      // Method to print student
      // details in main()
    @Override
    public String toString() {
        return name + " : " + age;
    }
}

// Comparator in a Helper Class
class CustomerSortingComparator 
          implements Comparator<Student> 
{
    
      // Compare first by name, then by age
    public int compare(Student customer1, Student customer2) {
        
          // Compare by name first
        int NameCompare = customer1.getName().compareTo(
                                  customer2.getName());
        
        // If names are the same, compare by age
        int AgeCompare = customer1.getAge().compareTo(
                                  customer2.getAge());
        
        // Return the result: first by name, second by age
        return (NameCompare == 0) ? AgeCompare : NameCompare;
    }
}

public class ComparatorHelperClassExample 
{
    public static void main(String[] args) 
    {
        List<Student> students = new ArrayList<>();
      
        students.add(new Student("Ajay", 27));
        students.add(new Student("Sneha", 23));
        students.add(new Student("Simran", 37));
        students.add(new Student("Ankit", 22));
          students.add(new Student("Anshul", 29));
          students.add(new Student("Sneha", 22));
      
          // Original List
        System.out.println("Original List ");

        // Iterating List
        for (Student it : students) {
            System.out.println(it);
        }
      
          System.out.println();

        // Sort students by name, then by age
          // using the CustomerSortingComparator
        Collections.sort(students, new CustomerSortingComparator());

        // Display message only
        System.out.println("After Sorting ");

        // Iterating using enhanced for-loop
        // after Sorting ArrayList
        for (Student it : students) {
            System.out.println(it);
        }
    }
}

Output
Original List 
Ajay : 27
Sneha : 23
Simran : 37
Ankit : 22
Anshul : 29
Sneha : 22

After Sorting 
Ajay : 27
Ankit : 22
Anshul : 29
Simran : 37
Sneha : 22
Sneha : 23

Alternative Method:

We can use the method mentioned below for achieving same results

students.sort(Comparator.comparing(Student::getName).thenComparing(Student::getAge));

Example:

Java
// Alternative Method
import java.util.*;

// Define the Student class
class Student {
    String name;
    Integer age;

    // Constructor
    Student(String name, Integer age) {
        this.name = name;
        this.age = age;
    }

    public String getName() {
        return name;
    }

    public Integer getAge() {
        return age;
    }

    // Method to print student details
    @Override
    public String toString() {
        return name + " : " + age;
    }
}

public class ComparatorHelperClassExample {
    public static void main(String[] args) {
        List<Student> students = new ArrayList<>();

        students.add(new Student("Ajay", 27));
        students.add(new Student("Sneha", 23));
        students.add(new Student("Simran", 37));
        students.add(new Student("Ankit", 22));
        students.add(new Student("Anshul", 29));
        students.add(new Student("Sneha", 22));

        // Original List
        System.out.println("Original List:");

        // Iterating List
        for (Student it : students) {
            System.out.println(it);
        }

        System.out.println();

        // Sort students by name, then by age
        students.sort(Comparator.comparing(Student::getName).thenComparing(Student::getAge));

        // Display message after sorting
        System.out.println("After Sorting:");

        // Iterating using enhanced for-loop after sorting ArrayList
        for (Student it : students) {
            System.out.println(it);
        }
    }
}

Output
Original List 
Ajay : 27
Sneha : 23
Simran : 37
Ankit : 22
Anshul : 29
Sneha : 22

After Sorting 
Ajay : 27
Ankit : 22
Anshul : 29
Simran : 37
Sneha : 22
Sneha : 23

Comparator vs Comparable

FeatureComparatorComparable
Sorting Logic LocationDefined externallyDefined within the class
Multiple Sorting OrdersSupportedNot supported
Interface Methodscompare()compareTo()
Functional InterfaceYesNo
UsageFlexible and reusableSimple and tightly coupled

Kickstart your Java journey with our online course on Java Programming, covering everything from basics to advanced concepts. Complete real-world coding challenges and gain hands-on experience. Join the Three 90 Challenge—finish 90% in 90 days for a 90% refund. Start mastering Java today!


Next Article
Article Tags :
Practice Tags :

Similar Reads

Why to Use Comparator Interface Rather than Comparable Interface in Java?
In Java, the Comparable and Comparator interfaces are used to sort collections of objects based on certain criteria. The Comparable interface is used to define the natural ordering of an object, whereas the Comparator interface is used to define custom ordering criteria for an object.Here are some reasons why you might want to use the Comparator in
8 min read
Stream sorted (Comparator comparator) method in Java
Stream sorted(Comparator comparator) returns a stream consisting of the elements of this stream, sorted according to the provided Comparator. For ordered streams, the sort method is stable but for unordered streams, no stability is guaranteed. It is a stateful intermediate operation i.e, it may incorporate state from previously seen elements when p
3 min read
Java | Collectors maxBy(Comparator comparator) with Examples
Collectors maxBy(Comparator<? super T> comparator) is used to find an element according to the comparator passed as the parameter. It returns a Collector that produces the maximal element according to a given Comparator, described as an Optional<T>. Syntax: public static <T> Collector<T, ?, Optional<T>> maxBy(Comparato
3 min read
Java | Collectors minBy(Comparator comparator) with Examples
Collectors minBy(Comparator<? super T> comparator) is used to find an element according to the comparator passed as the parameter. It returns a Collector that produces the minimal element according to a given Comparator, described as an Optional<T>. Syntax: public static <T> Collector<T, ?, Optional<T>> minBy(Comparato
4 min read
How to Fix java.lang.ClassCastException in TreeSet By Using Custom Comparator in Java?
This error is thrown by TreeSet because TreeSet is used to store elements in sorted order and if the specified element cannot be compared with the elements currently in the set then TreeSet won't be able to store elements in sorted order and hence, TreeSet throws class cast exception. How to fix this error? By providing a custom Comparator in TreeS
4 min read
PriorityQueue comparator() Method in Java
The java.util.PriorityQueue.comparator() method shares an important function of setting and returning the comparator that can be used to order the elements in a PriorityQueue. The method returns a null value if the queue follows the natural ordering pattern of the elements.Syntax: comp_set = (PriorityQueue)Priority_Queue.comparator() Parameters: T
2 min read
PriorityBlockingQueue comparator() method in Java
The comparator() method of PriorityBlockingQueue returns the comparator that can be used to order the elements in a PriorityBlockingQueue. The method returns null value if the queue follows the natural ordering pattern of the elements. Syntax: public Comparator<? super E> comparator() Returns: This method returns the comparator set used to or
2 min read
Comparator comparingInt() in Java with examples
The comparingInt(java.util.function.ToIntFunction) method accepts a function as parameter that extracts an int sort key from a type T, and returns a Comparator that compares by that sort key.The returned comparator is serializable if the specified function is also serializable. Syntax: static <T> Comparator<T> comparingInt(ToIntFunction
3 min read
How to Change the Comparator to Return a Descending Order in Java TreeSet?
Comparator interface is used to order the objects of user-defined classes. A comparator object is capable of comparing two objects of two different classes. TreeSet is one of the most important implementations of the SortedSet interface in Java that uses a Tree for storage. The ordering of the elements is maintained by a set using their natural ord
3 min read
Creating TreeSet with Comparator by User Define Objects in Java
TreeSet is the implementation class of Set Interface. It follows a natural sorting order or you can customize it using a comparator and it also does not allow duplicates. Syntax: TreeSet<String> gfg= new TreeSet<>(); Below is the normal implementation of the TreeSet: Java // Java program for TreeSet import java.io.*; import java.util.Tr
6 min read