Exemple de TreeSet avec Comparable en Java

Le premier exemple ci-dessous montre une erreur commise quand un objet est ajouté a une liste de type Set. Dans une Set, chaque élément doit etre unique, c'est pour cela qu'un objet doit etre  comparé avec les objets dans TreeSet avant qu'il soit inséré.

Premièrement, jetons un coup d’œil sur le code suivant qui crée trois objets "Point" et les ajoute à TreeSet.

import java.util.TreeSet;

class Point {
int x,y;
public Point(int x, int y){
this.x = x;
this.y = y;
}
}

public class ImpComparableWrong {

public static void main(String[] args) {
TreeSet d = new TreeSet();
d.add(new Point(2,4));
d.add(new Point(1,7));
d.add(new Point(5,3));

System.out.println(d.size());
}
}
La compilation et l'exécution retourne ce résultat:

Exception in thread "main" java.lang.ClassCastException: TreeSet.Point cannot be cast to java.lang.Comparable
at java.util.TreeMap.compare(Unknown Source)
at java.util.TreeMap.put(Unknown Source)
at java.util.TreeSet.add(Unknown Source)
at TreeSet.Comparable.main(Comparable.java:17)
La raison est que la classe Point a besoin d'implémenter l'interface Comparable pour permettre à TreeSet de contenir des objets Point. L'objet ajouté ne peut pas être comparé avec les éléments dans TreeSet, la méthode add() déclenche une exception ClassCastException. Pour rendre un objet comparable , il faut implémenter l'interface Comparable.

Le code suivant corrige cet erreur en implémentant l'interface Comparable:

import java.util.Iterator;
import java.util.TreeSet;

class Point implements Comparable{
int x,y;
public Point(int x, int y){
this.x = x;
this.y = y;
}

public int compareTo(Point p) {
double dp2 = (double) Math.sqrt(Math.pow(p.x,2) + Math.pow(p.y,2));
double dp = (double) Math.sqrt(Math.pow(x,2) + Math.pow(y,2));
if(dp > dp2)
return 1;
else
return 0;
}
}

public class Comparabletest {

public static void main(String[] args) {
TreeSet tset = new TreeSet();
tset.add(new Point(2,4));
tset.add(new Point(1,7));

Point a = new Point(2,5);

Iterator iterator = tset.iterator();
while(iterator.hasNext()){
Point p = iterator.next();
System.out.print(p.x +", "+ p.y);
System.out.println(" | p > a : "+p.compareTo(a));
}
}
}
Ce programme retourne en sortie ce résultat:

2, 4 | p > a : 0
1, 7 | p > a : 1
Références:
Javadoc: TreeSet class