Kiedy inter-pracy z kodem starszych, które nie określają parametry typu dla typów generycznych, należy użyć symbolu wieloznacznego. Na przykład, załóżmy, że są wywołanie metody w starszej biblioteki, które po prostu zwraca surowe Collection
:
Collection getItems();
W kodzie przypisać wynik do zmiennej zadeklarowanej asterisk:
Collection<?> items = widget.getItems();
ten sposób, zachowujesz bezpieczeństwo typu, więc nie otrzymasz żadnych ostrzeżeń.
Starsza wersja może określać (w komentarzu, najprawdopodobniej), jakie powinny być parametry ogólne. Na przykład:
/**
* @return the items, as a Collection of {@link Item} instances.
*/
Collection getItems();
W tym przypadku masz wybór. Możesz może rzucić wynik do Collection<Item>
, ale jeśli to zrobisz, polegasz w 100% na bibliotece strony trzeciej i odrzucasz pewność, że typy generyczne Java: że dowolny ClassCastException
podniesiony w czasie wykonywania nastąpi bezpośrednio po jawnym odlew.
Co zrobić, jeśli nie ufasz w pełni bibliotece firmy zewnętrznej, ale nadal musisz wygenerować numer Collection<Item>
? Następnie utwórz nową kolekcję i dodaj zawartość po przeniesieniu ich do oczekiwanego typu. W ten sposób, jeśli w bibliotece wystąpi błąd, od razu się o tym dowiesz, zamiast mieć jakiś kod daleko i znacznie później wysadzić w powietrze tajemnicę ClassCastException
.
Na przykład:
Collection<?> tmp = widget.getItems();
Collection<Item> items = new ArrayList<Item>(tmp.size());
for (Object o : tmp)
items.add((Item) o); /* Any type error will be discovered here! */
Dla przypadku, gdy parametr typu nie jest znany w czasie kompilacji, można użyć type-checked collection factories klasy Collections
.
Problem polega na tym, że tak naprawdę nie zyskuje nic innego jak wyciszanie ostrzeżeń "surowego typu". Konwersja na leki generyczne wymagałaby korzystania z jej zalet! –
Jakie są korzyści z leków generycznych? Nie powinno to sprawiać, że Twój kod wygląda ładnie i wymaga mniej pisania! Oto, co następuje: * Twój kod jest bezpieczny, jeśli kompiluje się bez ostrzeżeń. * To wszystko. Ignorując lub ukrywając ostrzeżenia, równie dobrze możesz nie używać generycznych, ponieważ wszystko, co robisz, tworzy sytuacje, w których kod bez operatora obsady w tajemniczy sposób podnosi "ClassCastException". – erickson