Anotações OCJP

Minhas anotações para o exame da Oracle (OCJP)

Arquivos Mensais: março 2011

O incrível comportamento de uma String

Alguem já parou para pensar na mecânica engenhosa que é a criaçao de uma String?
Sim, é uma construção fabulosa, que nos permite criar objetos sem explicitar o comando new:

class str{
public static void main(String args[]){
String s = "abc"
}
}

O processo de criação de uma string como acima, passa pela instância de um objeto String, atribuição do valor a este objeto e referencia deste objeto ao atributo de instância chamado de s.
Até agora, nenhuma surpresa para quem conhece java, parecem apenas detalhes de uma operação normal, mas existem algumas comparações com Strings que merecem alguma atenção:

class str2{
public static void main(String args[]){
String nome = "Bruno";
String nome2 = "Bruno";
String nome3 = new String("Bruno");
System.out.println(nome==nome2);//1
System.out.println(nome2==nome3);//2
System.out.println(nome.equals(nome2));//3
System.out.println(nome2.equals(nome3));//4
nome = nome3;
System.out.println(nome==nome2);//5
System.out.println(nome==″Bruno");//6
System.out.println(nome.equals(nome3));//7
}
}

Antes de compilar este codigo na jvm, tente ser o compilador. Nas linhas numeradas com comentários, quais são os resultados?
Depois de parar para pensar, confira se as respostas condizem com o que está abaixo:

1. True. Quando a jvm cria as Strings literais, ela armazena a referência desses objetos e localiza essa referência caso haja a comparação destes literais. Por isso que esta comparação retorna true.(Mais detalhes em http://www.guj.com.br/articles/103).

2. False. A referência para os objetos de nome2 e nome3 é diferente, pois um objeto novo é instanciado por nome 3 e a sua referência não funciona como as Strings literais.

3. True. O valor de nome é igual ao de nome2.

4. True. O valor de nome2 é igual ao de nome3.

5. False. A referência de nome agora é para o nome3, logo não é igual a referencia de literal.

6. False. Mesma justificativa da 5.

7. True. Os valores dos objetos são iguais.

Logo podemos concluir que as questões de String não são questões difíceis mas sim questões que exigem de nossa atenção.
Então é isso, até a próxima!

Anúncios

Interfaces e classes abstratas: Armadilha?

Começo os meus posts sendo bem direto: Até que ponto a herança em Java pode ser benéfica para aqueles que a usam?

Como diz aquela célebre frase: ” Grandes poderes trazem grandes responsabilidades.”

E é inegável que as interfaces trazem as responsabilidades para fazer nosso mundo melhor:

interface I{
void m1();
}

A interface acima deve ser implementada pela primeira classe concreta que a receber, o que seria facil de visualizar em um exemplo assim:

class C implements I{
public void m1(){
//...alguma coisa a programar
}
}

Porém, com a classe abstrata, a responsabilidade pode ser dividida. Muita atenção nesta parte:

interface J{
void m1();
String m2();
}

abstract class A implements J{
public void m1(){
//... algum código relevante
}
}

class C2 extends A implements J{
//m1 já foi implmentado por A, não é necessária mais a implementação

public String m2(){
//... mais código relevante
return "implementação de m2";
}

}

Pensei a princípio que daria erro, mas não, pois a classe C2 implementa os metodos m1 (pela classe A) e o método m2 (implementação na própria classe).

Mas o meu choque não parou por aí. Tinha muito mais a sair da manga do Sr. Java:

class C3{
void m1(){
System.out.println("m1.C3");
}
void m2(){
}
}
abstract class A2 extends C3{
abstract void m1();
}
class C4 extends A2{
void m1(){
System.out.println("m1.C4");
}
}
public class teste2{
public static void main(String args[]){
C3 c3 = new C4();
A2 a3 = new C4();
c3.m1();//saida m1.c4
a3.m1();//saída m1.c4
}
}

Não há erro algum neste código! O método m1 é redefinido como abstrato e depois e implementado pela classe C4.

E é isso, até a próxima!