Per ordinare liste di oggetti in Java sono a disposizione due interfacce:
- java.lang.Comparable
- java.util.Comparator
L’interfaccia java.lang.comparable di solito si utilizza per definire l’ordinamento “naturale” di un oggetto e consta di un metodo con firma
int compareTo(T o)
che paragona l’oggetto corrente (this) con l’oggetto fornito in input al metodo (o).
Il risultato sarà:
- un intero positivo se this>o
- 0 se sono uguali
- un intero negativo se this<0
Vediamo un esempio
|
|
public class Persona implements Comparable<Persona> { public Persona(){ } public Persona(String nome,String cognome,int eta){ this.nome=nome; this.cognome=cognome; this.eta=eta; } private String nome; private String cognome; private int eta; public String getNome() { return nome; } public void setNome(String nome) { this.nome = nome; } public String getCognome() { return cognome; } public void setCognome(String cognome) { this.cognome = cognome; } public int getEta() { return eta; } public void setEta(int eta) { this.eta = eta; } @Override public int compareTo(Persona o) { return this.cognome.compareTo(o.cognome); } public String toString(){ StringBuffer sb=new StringBuffer(); sb.append(this.cognome); sb.append(" "); sb.append(this.nome); sb.append(" "); sb.append(this.eta); return sb.toString(); }
}
|
|
L’ordinamento definito è sul cognome; si noti che utilizziamo il metodo compareTo dell’oggetto String che di default ordina in modo alfabetico crescente (A-Z).
L’interfaccia java.util.Comparator si utilizza invece quando si vogliono definire ordinamenti alternativi dell’oggetto.
Si crea dunque una classe a parte che implementa l’interfaccia con il seguente metodo:
public int compare(T a,T b);
Il risultato sarà:
- un intero positivo se a>b
- 0 se sono uguali
- un intero negativo se a<b
Vediamo un comparator che ordini le persone per età:
import java.util.Comparator;
public class PersonaEtaComparator implements Comparator<Persona> {
@Override public int compare(Persona p1, Persona p2) { int retVal=0; if(p1.getEta()>p2.getEta()) { retVal=1; } else if(p1.getEta()<p2.getEta()) { retVal=-1; } return retVal; }
} |
|
A questo punto vediamo il risultato eseguendo il seguente main; procederemo prima alla stampa dei record così come sono inseriti, poi ordinandoli per ordinamento naturale ed infine per età.
public class TestOrdinamento {
/** * @param args */ public static void main(String[] args) { LinkedList<Persona> lista=new LinkedList<Persona>(); popolaPersona(lista); System.out.println("Non ordinata>>"+lista); Collections.sort(lista); System.out.println("Ordinamento Naturale>>"+lista); Collections.sort(lista,new PersonaEtaComparator()); System.out.println("Ordinamento per età>>"+lista);
} private static void popolaPersona(LinkedList<Persona> lista) { lista.add(new Persona("mario","rossi",25)); lista.add(new Persona("luigi", "bianchi", 55)); lista.add(new Persona("mario","verdi",14)); lista.add(new Persona("luigi", "gialli", 45)); lista.add(new Persona("mario","maffei",32)); lista.add(new Persona("luigi", "servillo", 56)); }
} |
|
L’output prodotto dalle 3 liste sarà:
Non ordinata>>[rossi mario 25, bianchi luigi 55, verdi mario 14, gialli luigi 45, maffei mario 32, servillo luigi 56]
Ordinamento Naturale>>[bianchi luigi 55, gialli luigi 45, maffei mario 32, rossi mario 25, servillo luigi 56, verdi mario 14]
Ordinamento per età>>[verdi mario 14, rossi mario 25, maffei mario 32, gialli luigi 45, bianchi luigi 55, servillo luigi 56] |
|
Ma se volessi utilizzare un oggetto comparator per scrivermi da me un algoritmo di ordinamento senza affidarmi ad uno già implementato come dovrei fare??
RispondiEliminaPer esempio un metodo bubbleSort(Comparator) per una collezione Lista da voler usare magari su un'istanza concreta Lista...
Ciao, il Comparator serve soltanto a definire quale sarà il criterio di comparazione tra gli elementi.
RispondiEliminaIl metodo Collections.sort, come si legge dal javadoc, utilizza il mergesort per l'ordinamento (più efficiente del bubble sort).
Se quindi dovessi implementare un bubble sort senza affidarmi al default allora mi creerei una mia classe MyCollections con un metodo sort(List list,Comparator c) al cui interno implementerei la mia logica.