Java: récupère tous les noms de variables d'une classe

91

J'ai une classe et je veux trouver tous ses champs publics (pas les méthodes). Comment puis-je faire ceci?

Merci!

ufk
la source
Vous devriez pouvoir le faire à l'aide de l' API Reflection .
Crozin

Réponses:

134
Field[] fields = YourClassName.class.getFields();

renvoie un tableau de toutes les variables publiques de la classe.

getFields()renvoyer les champs dans toute la classe-héritage. Si vous souhaitez que les champs soient définis uniquement dans la classe en question, et non dans ses superclasses, utilisez getDeclaredFields()et filtrez publiccelles-ci avec l' Modifierapproche suivante :

Modifier.isPublic(field.getModifiers());

Le YourClassName.classlittéral représente en fait un objet de type java.lang.Class. Consultez sa documentation pour des méthodes de réflexion plus intéressantes.

La Fieldclasse ci-dessus est java.lang.reflect.Field. Vous pouvez jeter un œil à l'ensemble du java.lang.reflectpackage.

Bozho
la source
2
juste une note - au départ, ma réponse contenait une mauvaise déclaration, mais elle a été votée plusieurs fois. Veuillez lire plus attentivement;)
Bozho
1
@downvoter - l'erreur était avant. Si vous en voyez un maintenant, partagez-le.
Bozho
cette solution est-elle lente? ou pouvons-nous l'utiliser librement?
Dany Y
c'est bon. Mais n'en abusez pas.
Bozho
15

Vous pouvez utiliser l'un des deux en fonction de vos besoins:

Field[] fields = ClassName.class.getFields(); // returns inherited members but not private members.
Field[] fields = ClassName.class.getDeclaredFields(); // returns all members including private members but not inherited members.

Pour filtrer uniquement les champs publics de la liste ci-dessus (en fonction des exigences), utilisez le code ci-dessous:

List<Field> fieldList = Arrays.asList(fields).stream().filter(field -> Modifier.isPublic(field.getModifiers())).collect(
    Collectors.toList());
Sahil Chhabra
la source
2

Comme mentionné par quelques utilisateurs, le code ci-dessous peut aider à trouver tous les champs d'une classe donnée.

TestClass testObject= new TestClass().getClass();
Method[] methods = testObject.getMethods();
for (Method method:methods)
{
    String name=method.getName();
    if(name.startsWith("get"))
    {
        System.out.println(name.substring(3));
    }else if(name.startsWith("is"))
    {
        System.out.println(name.substring(2));
    }
}

Cependant, une approche plus intéressante est ci-dessous:

Avec l'aide de la bibliothèque Jackson, j'ai pu trouver toutes les propriétés de classe de type String / integer / double, et les valeurs respectives dans une classe Map. ( sans utiliser l'API Reflections! )

TestClass testObject = new TestClass();
com.fasterxml.jackson.databind.ObjectMapper m = new com.fasterxml.jackson.databind.ObjectMapper();

Map<String,Object> props = m.convertValue(testObject, Map.class);

for(Map.Entry<String, Object> entry : props.entrySet()){
    if(entry.getValue() instanceof String || entry.getValue() instanceof Integer || entry.getValue() instanceof Double){
        System.out.println(entry.getKey() + "-->" + entry.getValue());
    }
}
Amit Kaneria
la source