? extends HasWord
oznacza „klasę / interfejs, który się rozszerza HasWord”. Innymi słowy, on HasWordsam lub którekolwiek z jego dzieci ... w zasadzie wszystko, co działałoby z instanceof HasWordplusem null.
Mówiąc bardziej technicznie, ? extends HasWordjest to symbol wieloznaczny ograniczony, objęty pozycją 31 Effective Java 3rd Edition , począwszy od strony 139. Ten sam rozdział z 2nd Edition jest dostępny online w formacie PDF ; część ograniczonych symboli wieloznacznych to pozycja 28, począwszy od strony 134.
Aktualizacja: link PDF został zaktualizowany, ponieważ Oracle usunął go jakiś czas temu. Teraz wskazuje na kopię hostowaną przez School of Electronic Engineering and Computer Science na Queen Mary University of London.
Aktualizacja 2: Przejdźmy trochę bardziej szczegółowo do tego, dlaczego chcesz używać symboli wieloznacznych.
Jeśli zadeklarujesz metodę, której podpis spodziewasz się przekazać List<HasWord>, jedyną rzeczą, którą możesz przekazać, jest List<HasWord>.
Jeśli jednak wspomniany podpis List<? extends HasWord>byłby, można List<ChildOfHasWord>zamiast tego przekazać .
Zauważ, że istnieje subtelna różnica między List<? extends HasWord>i List<? super HasWord>. Jak ujął to Joshua Bloch: PECS = producent rozszerza, konsument super.
Oznacza to, że jeśli przekazujesz kolekcję, z której twoja metoda pobiera dane (tj. Kolekcja wytwarza elementy do użycia przez metodę), powinieneś jej użyć extends. Jeśli przekazujesz kolekcję, do której twoja metoda dodaje dane (tj. Kolekcja zużywa elementy tworzone przez twoją metodę), należy jej użyć super.
Może to brzmieć myląco. Jednak można go zobaczyć w List„ssort polecenia (które jest po prostu skrót do wersji dwu-Arg z Collections.sort). Zamiast brać Comparator<T>, w rzeczywistości zajmuje Comparator<? super T>. W takim przypadku Komparator zużywa elementy List, aby zmienić kolejność samej listy.