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

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

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.

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”

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.

Sérgio pode crer

Ficou sinistro trocar o 12 por 1000 iauhuiahuiah

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

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).

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?

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.

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 “newcria novos objetos.

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

[code]String s1 = “Java”;
String s2 = “Java”;

s1 == s2 // true

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

s3 == s4 // false[/code]

Espero ter ajudade em alguma coisa

Um abração e sucesso pra você

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