Pessoal,
Tenho essa declaração de método:
public static <T> List<T> backwards(List<? super T> input){ return null;}
Mas não entendi o ? super T. O que essa linha esta fazendo?
Pessoal,
Tenho essa declaração de método:
public static <T> List<T> backwards(List<? super T> input){ return null;}
Mas não entendi o ? super T. O que essa linha esta fazendo?
Qualquer classe que seja T ou ancestral de T.
esse :?: é um tipo curiga que vc está defindo.
? super T
esta dizendo que recebe como parametro qq coisa que esteja acima de sua sub-class na hierarquia de T.
se Cliente extends Pessoa…vc assumiria que T = Pessoa…
agora se fizer isso.
? extends T
esta dizendo que tudo que for subclasse de T.
num sei se ficou claro pra vc, qq coisa posta ai.
vlw!
uma coisa q não entendi tb…como ele coloca dois tipos de retorno???
public static List backwards(List<? super T> input){
só deixando claro que em
"? super T" o T também está incluído, ou seja aceita qualquer super classe de T e o próprio T
o mesmo é valido para “? extends T”, aceita qualquer sub-classe de T e o próprio T
o antes do List serve para declarar o tipo , já que T é um genérico.
Se não fosse assim, ele esperaria que T fosse uma interface/classe
[quote=mueller]o antes do List serve para declarar o tipo , já que T é um genérico.
Se não fosse assim, ele esperaria que T fosse uma interface/classe
[/quote]
HUmm…perai…xa eu ver se entendi…quando eu coloco assim List estou dizendo que retornara um objeto genérico T mas especializado para um List genérico?
Acho que assim fica mais fácil para explicar o porquê desse . Se você tiver um método assim
public List<String> getFoo(){...}
Você sabe que vai retonar lista de string, não consegue usar esse método para retornar lista de inteiros.
Agora quando você constrói um método genérico
public List<T> getFoo(){...}
(esse código não compila) a jvm não vai entender o que é esse <T> (exceto se você tiver uma interface/classe T), por isso você declara ele na assinatura do método, assim
isso não é mt usado no dia-a-dia neh? só em certificação pelo jeito
Não é só certificação, minha explicação não ficou boa, esse é fundamental para o uso de generics
Vamos lá denovo.
Imagine que você tem um método que recebe 2 objetos List, seu método precisa criar um Set e unir as 2 lists. O método também precisa ser genérico, deve trabalhar com listas de qualquer elemento.
Sem generics ficaria assim:
public Set unir(List lista1, List lista2){
Set s = new HashSet(lista1);
s.addAll(lista2);
return s;
}
Sem utilizar o generic, você vai precisar fazer um cast quando chamar esse método, além de receber alguns warnings.
Agora para fazer esse método funcionar sem cast nem warnings, você reescreve assim
public <T> Set<T> unir(List<T> lista1, List<T> lista2){
Set<T> s = new HashSet<T>(lista1);
s.addAll(lista2);
return s;
}
Agora ele trabalha com listas de qualquer objeto, da mesma forma que o exemplo anterior só que sem a necessidade de cast e sem warnings.
Então você pode usar um
Set<String> setStrings = unir(umaListaStrings, outraListaStrings);
Set<Integer> setInteger = unir(umaListaIntegers, outraListaIntegers);
O então que era a dúvida, é parte fundamental dos generics.
agora q eu entendi q é um simples cast…hehehe