Análise das dependencias de uma classe

8 respostas
T

Pessoal,

estou em um projeto pessoal e no momento estou com um problema: dado uma classe(arquivo .java) como saber de quais classes esta primeira classe depende?

Eu teria que ler a classe e descobrir atributos, classe mãe, interface(caso implemente alguma), parâmetros e retorno de métodos, classes internas, etc etc etc.

Entretanto imagino que exista alguma biblioteca que faça isso já procurei mas não encontrei o que buscava.

Vocês conhecem alguma biblioteca ou recurso que possa me ajudar?

Grato,
Talles Santana

8 Respostas

D

Pq vc precisa dessa informação?

Uma classe depende da classe que ela herda (e por consequencia de toda a sua hierarquia de herança), das classes que a compoem (suas partes), das classes que ela usa em seus métodos, mas que não são suas partes, etc.

Acho que se vc explicar o que você precisa fazer, ou pq precisa saber essas informações, fica mais fácil te ajudar.

[]'s

M

cara, mexo com compiladores, analisadores lexicos, sintaticos entre algumas outras coisas, para vc fazer isso, o correto é vc construir, nessa ordem:

1 - transformar cada letra do seu codigo em um char e incluir esse char em uma lista
2 - construir um analisador lexico, onde vc vai pegar cada char que foi feito no passo 1 e juntalos em tokens que façam sentido para a linguagem, por exemplo, se vc tem o conjunto de char ‘n’, ‘e’, ‘w’, vc sabe que na linguagem Java isso é uma palavra reservada, vc deve pegar esses 3 chars e transformar em 1 token “new” e incluila em uma List
3 - depois que o passo 1 e 2 estiverem concluidos, vc deve construir um “filtro” para percorrer essa sua List de tokens e verificar depois dos tokens do tipo “import” qual é a dependencia direta, o proximo passo é pegar as classes que estão no mesmo pacote, que não necessitam serem importadas, verificar o que existe depois do token “extends”, e por ai vai…

acho que não fui muito claro, mas esse assunto é um pouco complicado para explicar somente escrevendo em poucas linhas.

qualquer coisa estamos ai.

abraços!!

D

Construir um analisador léxico na mão???
Além de não resolver o problema pq vc só vai saber se cada token faz parte da linguagem, é extremamente propenso a erros.
Se tiver mesmo que implementar algum tipo de analisador, o ideal seria usar um gerador de analisadores, como o ANTLR.
Não concordo com a solução do mcbarsotti em diversos aspectos. Imagine um import com “*”. E ai? Como fica?

Como falei, acho que seria legal vc explicar o que precisa fazer, fica mais fácil de ajudar, pq as vezes o problema pode ser contornado de outra forma.
Explique o que são “dependências” para você, pois muita informação pode ser obtida através de reflexão da classe. Se as dependências que você precisa são as que você citou, reflexão resolve o problema.

Vou fazer um exemplo aqui…

[]'s

D

Olha o exemplo:

import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.lang.reflect.Modifier;
import javax.swing.JOptionPane;

/**
 *
 * @author David Buzatto
 */
public class TestesReflexao {

    public static void main(String[] args) {
        reflect( JOptionPane.class );
    }

    public static void reflect( Class klass ) {

        System.out.println( "Classe: " + klass.getSimpleName() );
        System.out.println( "Pacote: " + klass.getPackage().getName() );
        System.out.println( "Nome completo: " + klass.getCanonicalName() );

        System.out.println();

        System.out.println( "Campos: " );
        for ( Field f : klass.getDeclaredFields() ) {
            System.out.println( "Nome: " + f.getName() );
            System.out.println( "Tipo: " + f.getType() );
            System.out.print( "Modificadores: " );
            listModifiers( f.getModifiers() );
            System.out.println();
        }

        System.out.println( "Métodos: " );
        for ( Method m : klass.getDeclaredMethods() ) {
            System.out.println( "Nome: " + m.getName() );
            System.out.println( "Tipos dos parâmetros: " );
            for ( Class k : m.getParameterTypes() ) {
                System.out.println( "    " + k );
            }
            System.out.println( "Tipo de Retorno: " + m.getReturnType() );
            System.out.print( "Modificadores: " );
            listModifiers( m.getModifiers() );
            System.out.println();
        }



    }

    private static void listModifiers( int mod ) {

        if ( Modifier.isPrivate( mod ) ) {
            System.out.print( "private " );
        }

        if ( Modifier.isPublic( mod ) ) {
            System.out.print( "public " );
        }

        // outros modificadores aqui...

    }

}

Estude a API de reflexão (java.lang.Class e todas as classes do pacote java.lang.reflect).

[]'s

T

Eu acho que o Talles está querendo algum plugin ou ferramenta que faça um diagrama de classe para ele.
Seria isso Talles?
Se não engano já vi um plugin do Eclipse que faça isso.

M

porque não? isso faz parte do meu trabalho, todo santo dia. :frowning:

Não entendi…

e usar o ANTLR também está propenso a erros. Os erros são evitados fazendo testes, isso usando ANTLR, lexico, parser na mão ou qualquer outra coisa.

Não diria “ideal” e sim “uma outra opção”.

No caso do import com “*”, não é pq vc escreveu um import … * em seu código que essa classe depende de todas as classes que estão nesse pacote, você pode importar 1 milhão de classes mas só usar 2, certo??

btw, acho que a solução do davidbuzatto é mais uma opção para vc avaliar e que também pode resolver o seu problema, o legal é que vc já tem pelo menos 2 caminhos que vc pode escolher seguir.

essa thread está com uma discussão muito bacana, é dificil encontrar assuntos desse tipo nos foruns por ai…

ABS

T

davidbuzatto:

Estude a API de reflexão (java.lang.Class e todas as classes do pacote java.lang.reflect).

[]'s

Valeu pela dica. Já tinha usado Reflection mas foram outras coisas e eu tinha esquecido que a API tinha tanto recurso.

Vou tentar caminhar mais um pouco no projeto.

O que eu quero fazer é apenas um plugin para eclipse que mostra as dependencias de uma classe. Considerando dependencia o que eu falei anteriormente:
Dado uma classe (A)
a) herdar de uma classe (B)
b) implementar uma interface (B)
c) utilizar atributos/constantes do tipo de uma classe (B)
d) receber como parametros de métodos um tipo de uma classe (B)
e) retornar como parâmetros de métodos um tipo de uma classe (B)

Ainda não considerei um cenário de uma inner class, isso é mais para a frente: um passo de cada vez :wink:

[]'s

T

Pessoa, faltou um cenário que caracteriza dependência que não é possível ser resolvido por reflexão.
Uma classe A instancia/utiliza uma classe B dentro de um método( ou bloco qualquer) sem que B seja retorno do método.

Então, vocês conhecem alguma biblioteca que me ajude nessa tarefa?

[]'s

Criado 4 de fevereiro de 2011
Ultima resposta 9 de fev. de 2011
Respostas 8
Participantes 4