Classe Object: pergunta besta, mas

9 respostas
J

Cara uma dúvida besta, trabalho com java a algum tempo, mas só parei para pensar nisso agora.

Se a classe Object é a raiz de tudo, como ela pode fazer referencia a classe String, no método toString() se a classe String é uma sub classe do Object e consequentemente precisa do object definido para ser compilada?

Eu sei que parece uma pergunta idiota, mas…

EDIT:
Encontrei isso no code ranch, de um cara que tb teve essa dúvida
http://www.coderanch.com/t/522615/java/java/Dependency-between-String-Object-class

Mas essa história de dependencia circular é bem estranha. Do meu ponto de vista a classe Object não deveria depender de nenhuma outra.

9 Respostas

MaYaRa_SaN

boa pergunta ahahaha

vai na mesma linha de quem nasceu primeiro, o ovo ou a galinha?

na documentação nao fala nada… fiquei intrigada agora!

ivo_costa

O compilador compila as duas ao mesmo tempo.
Pode fazer um teste ae, cria uma classe X que usa a classe Y e na classe Y colocar um referência para X. Quando tu compilar a X a Y tbm será compilada.

doravan

Ao compilar uma das duas vai ser suficiente, o javac vai compilar ambas.
A dependência nesse caso é resolvida durante a compilação.

J

É… eu fiz o teste e realmente funciona.

Mas só eu acho estranho a classe principal do Java depender de uma segunda classe, e essa segunda classe extender a classe principal? Só eu acho que isso parece gambiarra?

E

Vou contar um segredo. Há várias classes que estão na definição da linguagem (String, os wrappers java.lang.Integer e seus amigos) que são definidas como “predefinidas” - ou seja, se você fosse compilar o fonte da classe java.lang.Object, a definição da classe java.lang.String já estaria conhecida, e vice-versa.
O compilador Java depende de que as definições das classes que ele usa estejam em alguns jars predefinidos, como o rt.jar. A primeirissíma versão do rt.jar (que era chamada classes.zip), no tempo em que o Java não se chamava “Java” e sim Oak, provavelmente teria alguns arquivos .class criados “no braço” ou por alguma outra ferramenta que não o javac (que é obviamente um programa muito complicado em Java).
Portanto, o dilema de que a classe java.lang.Object depende de uma filha dela para existir na verdade não existe.

E

E de fato, em condições normais, não se pode fazer uma classe depender de uma filha dela para existir, conforme você deve ter suspeitado.
Uma das exceções conhecidas é a java.lang.Object justamente porque supõe-se que todas as classes do pacote java.lang.* existem e foram criadas “ao mesmo tempo”, que é somente uma ficção.

J

Ok, mas ainda não ficou claro para mim de se isso é uma prática aceitável, ou execrável do tipo “Fizemos pq tinha que ser feito assim, mas nunca NUNCA o faça tb”. Pergunto pq alguns livros apontam modelagens bem questionáveis nas primeiras versões do Java, que temos que conviver com eles até hoje.

E

Se você olhar a implementação de outras classes do JDK também vai ver certas dependências esquisitas, que só são justificáveis porque houve uma versão 0.00000 do Java (talvez ainda chamada de Oak) que foi usada para gerar o primeiro .class :slight_smile:
Você está pensando no problema de “bootstrap” em compiladores. O primeiro compilador Java provavelmente não foi escrito em Java e sim em C ou C++, e depois deve ter sido jogado fora, e ainda por cima deveria provavelmetne considerar algumas classes como predefinidas (como java.lang.String, que pode ser considerada uma espécie de “classe primitiva da linguagem”, embora ela não seja exatamente isso pela definição).

E

Aliás, você deve ter percebido que há várias classes e interfaces que são especiais no Java - o compilador tem de “nascer sabendo” que elas existam:

java.lang.String - existem constantes String, o que não ocorre para nenhuma outra classe.  Além disso, ela é declarada final, não  por motivos de segurança, mas para evitar outros problemas esquisitos que ocorreriam se ela não fosse "final.

java.lang.Integer, java.lang.Double, java.lang.Boolean, java.lang.Float, java.lang.Void, java.lang.Short, java.lang.Character - são classes usadas no autoboxing, por exemplo. O Autoboxing supõe que essas classes existam.

java.lang.Iterable - para o for ( : )

java.lang.AutoCloseable - para o try with resources (recurso novo do Java 7)

java.lang.Throwable, java.lang.Exception, java.lang.RuntimeException - para o try/catch

java.lang.Class - para a constante simbólica .class

java.lang.Enum - todas as Enums são filhas desta classe

java.lang.annotation.Annotation - todas as Annotations implementam esta interface
Criado 28 de outubro de 2011
Ultima resposta 28 de out. de 2011
Respostas 9
Participantes 5