Il s'agit d'une méthode qui permet à une classe étendant une classe générique ou implémentant une interface générique (avec un paramètre de type concret) d'être toujours utilisée comme un type brut.
Imaginez ceci :
public class MyComparator implements Comparator<Integer> {
public int compare(Integer a, Integer b) {
//
}
}
Il ne peut pas être utilisé dans sa forme brute, en passant deux Object
à comparer, car les types sont compilés dans la méthode de comparaison (contrairement à ce qui se passerait s'il s'agissait d'un paramètre de type générique T, où le type serait effacé). Au lieu de cela, en coulisses, le compilateur ajoute une "méthode de pont", qui ressemble à quelque chose comme ceci (s'il s'agissait d'une source Java) :
public class MyComparator implements Comparator<Integer> {
public int compare(Integer a, Integer b) {
//
}
//THIS is a "bridge method"
public int compare(Object a, Object b) {
return compare((Integer)a, (Integer)b);
}
}
Le compilateur protège l'accès à la méthode bridge, en faisant en sorte que les appels explicites à cette méthode entraînent une erreur de compilation. Maintenant, la classe peut également être utilisée dans sa forme brute :
Object a = 5;
Object b = 6;
Comparator rawComp = new MyComparator();
int comp = rawComp.compare(a, b);
Pour quelle autre raison serait-elle nécessaire ?
Outre l'ajout de la prise en charge de l'utilisation explicite des types bruts (principalement pour des raisons de compatibilité ascendante), les méthodes de pontage doivent également prendre en charge l'effacement des types. Avec l'effacement des types, une méthode comme celle-ci :
public <T> T max(List<T> list, Comparator<T> comp) {
T biggestSoFar = list.get(0);
for ( T t : list ) {
if (comp.compare(t, biggestSoFar) > 0) {
biggestSoFar = t;
}
}
return biggestSoFar;
}
est en fait compilé en bytecode compatible avec celui-ci :
public Object max(List list, Comparator comp) {
Object biggestSoFar = list.get(0);
for ( Object t : list ) {
if (comp.compare(t, biggestSoFar) > 0) { //IMPORTANT
biggestSoFar = t;
}
}
return biggestSoFar;
}
Si la méthode de pontage n'existait pas et que vous passiez une méthode List<Integer>
et un MyComparator
à cette fonction, l'appel à la ligne marquée IMPORTANT
échouerait puisque MyComparator
n'aurait pas de méthode appelée compare
qui prend deux Object
s...seulement un qui prend deux Integer
s.
La FAQ ci-dessous est une bonne lecture.
Voir aussi :
14 votes
Je ne peux pas l'expliquer plus clairement que ça : stas-blogspot.blogspot.com/2010/03/ (qui se trouve être le 1er résultat de google)