Escolar Documentos
Profissional Documentos
Cultura Documentos
Object
Compartilhar
Para entender melhor a decisão da Sun em cada uma dessas assinaturas de métodos você
sempre precisa levar em conta dois pontos: erasure e o uso do coringa. Antes vamos
relembrar esses conceitos. Considere o código que imprime uma lista de objetos
Comparable:
Agora podemos passar uma List<String>, pois isso é uma List<? extends
Comparable>, isto é, uma lista de algum tipo que é compatível com Comparable.
Porque então não usamos sempre esse idiomismo? Repare então no seguinte método:
Aqui temos o mesmo problema. Não podemos receber como referência uma
List<String>! Vamos tentar aplicar o mesmo procedimento:
public void adicionaString(List<? extends Comparable> lista) {
lista.add("caelum"); // não podemos invocar métodos que recebem o
tipo
// parametrizado (a menos que seja passado null)
}
O código acima não compila! Isso ocorre porque List<? extends Comparable> pode
receber uma lista de qualquer tipo que seja Comparable. Se isso fosse possível, alguém
poderia passar como argumento uma List<Integer>, e no fim do método esta lista de
inteiro estaria contendo uma String, quebrando o contrato novamente!
Como resolver esse problema? Não tem como! Se você recebe um objeto parametrizado
pelo coringa ?, você nunca poderá invocar um método desse objeto, porque você não
sabe qual o tipo que ele realmente aceita! A linguagem não permite isso porque não
sabe exatamente o que você vai fazer com esse objeto. Em alguns casos,
semanticamente, apesar de um método receber um tipo parametrizado, não tem
problema ele receber um objeto que não esteja de acordo com seu tipo parametrizado.
Esse é exatamente o caso do método contains: não haveria problema de passar um
Integer para o contains de uma List<String>! Mas se contains recebesse E, o
seguinte código não compilaria:
A API de coleções traz assinaturas muito mais estranhas. Eu demorei bastante até
entender por completo a assinatura de alguns métodos da Collections, como por
exemplo o Collections.min: