The Comparator interface

In the previous post about the Comparable interface I explained how you can extend a class of objects that implement the Comparable interface and then order them in a list according to the logic defined in the overridden method compareTo.
If you want to be able to sort the list according to a number of different criteria you must use the Comparator interface, for example, in the case of a list of countries, it is possible that you want to order them not only alphabetically but also in order of area or population.
A very important difference between Comparable and Comparator is as follows:

  • using Comparable, you must modify the object class you want to sort implementing Comparable
  • using Comparator, you must create a new class that implements Comparator; this new class can be a public class in its own file. java, or can also be an inner class because it is intimately tied to the outer class of objects to be sorted

The only method required by the Comparator interface is compare which has as argument 2 objects of the same type you are sorting and the return value is an integer.
So the call to the method is:
int result = compare(x, y)
where x and y are objects of the same type of those in the list and result is an integer that takes the value:

  • <0 if x<y
  • ==0 if x==y
  • >0 if x>y

After you have created the class Comparator you can use the static method Collections.sort(List list, Comparator c) to sort the list.
Look at the following example:

  • Main.java
  • Country.java

The output is:

The class Country implements Comparable, this is not necessary to use Comparator but it is only useful to be able to make a comparison.
In the class Country there are 2 static inner classes (static to be used without an instance of the class Country) that override the compare method.
There are 4 sections in Main.java: in the first section the sort is by name without using Comparator but only the Comparable interface, in the second section the sort is by area; in the third section of the sort is descending by population (reverseOrder (Comparator cmp) returns a comparator that imposes the reverse ordering of the specified comparator); in the fourth section the sort is descending by name (reverseOrder () returns a comparator that imposes the reverse order of that defined in the Comparable interface).

Similarly, you can also sort the arrays using the Arrays.sort(Object[] a, Comparator c) method.

6 Comments

 Add your comment
  1. Salve.. complimenti per l’articolo mi è stato molto d’aiuto.. mi chiedevo se a posto delle liste avremmo usato dei Set ad esempio TreeSet, nel momento in cui ordiniamo con un Comparator esso eliminerà ad esempio due nazioni con la stessa popolazione o la stessa area, è possibile ovviare a questo problema? oppure è necessario affidarsi a Comparable implementando hashCode e equals riguardanti il solo nome della nazione? grazie

    • Per evitare di aggiungere oggetti uguali è possibile usare l’interfaccia Set ma gli oggetti devono implementare il metodo equals che definisce cosa si intende per uguali.
      In tal caso oggetti uguali possono essere creati ma non aggiunti contemporaneamente al Set

  2. Ciao!
    Solo una domanda.

    Perchè il metodo “compare” delle varie classi AreaComparator e PopolutazionComparator viene chiamato in automatico alla creazione di un istanza delle due classi? Come mai non hai bisogno di fare un “.compare(var 1 var 2)” da nessuna parte?

    Grazie 1000 se mi togli un po di confusione!

    • Il metodo compare non è usato chiamandolo direttamente, al metodo sort di Collections passi come argomento la lista da ordinare e una classe che implementa Comparator e quindi il metodo compare, sarà poi il metodo Collections.sort che chiamerà il metodo compare nel codice sorgente di java

  3. Cioè ti ringrazio non una ma diecimila volte…
    Seguendo corsi all’università,vari tutorial su internet,rileggendomi ventimilavolte le pagine del libro su quest’argomento non sono mai riuscita a capirlo…sono venuta qui ed ho seguito passo passo ciò che hai scritto implementando anche le classi….e finalmente ci sono riuscita…
    Te ne sono veramente grata…

Leave a Comment

Your email address will not be published.