Dúvida com comparações == e equals em Wraper [RESOLVIDO]

9 respostas
brunorota

Olá galera

Me deparei com o primeiro exercício assim hehehe

Ainda bem que foi antes da prova

Gostaria saber o que acontece por traz dos panos na comparação, Exemplo:

Integer i1 = 12;
Integer i2 = 12;

System.out.println(i1 == i2); //true

Integer f1 = new Integer(12);
Integer f2 = new Integer(12);

System.out.println(f1 == f2);; //false

Porque instanciando com a palavra new o resultado com == é false?

Eu sei que é seguro comparar com equals que sempre vai comparar os valores

Se alguem tiver um tempinho para me explicar ^^

Atenciosamente

9 Respostas

sergiolopes

Se quiser ficar ainda mais confuso, faça o mesmo exercício mas troque o valor 12 por 1000 e se surpreenda :slight_smile:

A explicação aqui é que == envolvendo objetos, sejam eles quais for (Integer, String, ContaCorrente etc) sempre comparam referências. Então quando você dá new você me explicitamente dois objetos diferentes, cada um em sua referência, e aí é óbvio que == vai dar false.

Mas aí você se pergunta: porque o 1o caso dá true? Ele compara valor? Não, nunca. O == sempre compara referências. Só que no primeiro caso as referências são a mesma por uma combinação de fatores, e portanto o resultado é true.

Para entender é importante saber o que faz o autoboxing do Java 5. Ele não dá new explicitamente (ou seja, o 1o caso é diferente do 2o caso). O autoboxing sempre usa Integer.valueOf para embrulhar o valor. Na pratica, essas duas expressoes são equivalentes:

Integer i = 12;
Integer i = Integer.valueOf(12);

Por fim, sabendo disso, se voce ler o javadoc do valueOf vai quer que nem sempre esse método cria novos objetos. Ele pode ter um cache interno de Integers mais usados e apenas devolver a mesma referência se for pedido mais de uma vez. Aqui voce ja deve ter desconfiado que é exatamente o que acontece ao atribuir 12 a duas varias diferentes: ele devolve o mesmo objeto e temos duas referencias para o mesmo objeto.

sergiolopes

Ah acabei de perceber que o seu exercicio nao é o mais legal: se fizer o teste de i1==i2 aí sim fica divertido trocar o 12 pelo 1000 hehehe

No seu caso, i1==12 vai causar o unwrap de i1 e vai ser equivalente a “i1.intValue()==12”

Hebert_Coelho

Pois é cara, traduzindo, vc pode fazer assim que vai funcionar:

Integer a = 10;
		Integer b = 10;
		System.out.println(a.equals(b));
		int c = 10;
		int d = 10;
		System.out.println(c == d);

Tenha em mente que ao comparar primitivos (int, long, e tals) aí rola de mandar um ==.

Quando se trata de classes (Wrapper como Integer, ou até mesmo Cliente q vc venha criar) utilize equals.

No caso, Integer, String já vem com equals implementados, se for uma classe que vc esteja criando, vc terá que implementar.

brunorota

Sérgio pode crer

Ficou sinistro trocar o 12 por 1000 iauhuiahuiah

Tem alguma explicação porque isso acontece? =P

Ataxexe

Quando você usa 1000 o valueOf não utiliza o cache (que vai de -128 a um valor configurado pela propriedade “java.lang.Integer.IntegerCache.high” - caso não exista é usado 127).

mjohnatha

Não tenho 100% de certeza agora.
Mas, se não me engano, para Short e Integer, quando os valores estão entre -128 e 127, o resultado da comparação é true;
caso contrário, o resultado é false.
Parece que a JVM faz isso para economizar memória, ou algo parecido.

Porém, repito: não tenho certeza.

Alguém pode confirmar?

Ataxexe

Como disse no post acima, é mais ou menos verdade. Você pode configurar o valor máximo do cache para o tipo Integer. Para os demais (Short e Long) é usado 127 como valor máximo.

deyvid

Bem eu não li as respostas dos nossos colegas mas eis minha resposta

1. Integer i1 = 12;  
2. Integer i2 = 12;  
3.   
4. System.out.println(i1 == i2); //true  
5.   
6. Integer f1 = new Integer(12);  
7. Integer f2 = new Integer(12);  
8.   
9. System.out.println(f1 == f2);; //false

Por não usar "new" i1 e i2 estão se referindo ao mesmo objeto. O que não acontece com f1 e f2, que quando usa a keyword "new" cria novos objetos.

Tirei essa resposta baseado numa questão que respondi essa semana que era mais ou menos

String s1 = "Java";
String s2 = "Java";

s1 == s2 // true

String s3 = new String(s1);
String s4 = new String(s2);

s3 == s4 // false

Espero ter ajudade em alguma coisa

Um abração e sucesso pra você

brunorota

Opaa

Se cair uma dessa com ctz eu nao erro hehehe

Valew a todos ae pelas respostas

Se tudo der certo, sexta feira eu coloco um post aqui sobre a prova ^^

VAleww

Criado 27 de julho de 2010
Ultima resposta 27 de jul. de 2010
Respostas 9
Participantes 6