interfaz - swing java
Cómo acceder al valor de un campo en un objeto usando la reflexión (2)
Antes de get
un campo privado, debe llamar a setAccessible(true);
en el campo correspondiente:
for (Field field : fields) {
field.setAccessible(true); //Additional line
System.out.println("Field Name: " + field.getName());
System.out.println("Field Type: " + field.getType());
System.out.println("Field Value: " + field.get(person));
}
Mi pregunta: Cómo superar una IllegalAccessException
para acceder al valor del campo de un objeto usando reflection.
Expansión: estoy tratando de aprender sobre la reflexión para hacer que algunos de mis proyectos sean más genéricos. Me encuentro con una IllegalAccessException
cuando intento llamar a field.getValue(object)
para obtener el valor de ese campo en ese objeto. Puedo obtener el nombre y tipo bien.
Si cambio la declaración de private
a public
entonces esto funciona bien. Pero en un esfuerzo por seguir las "reglas" de la encapsulación, no quiero hacer esto. ¡Cualquier ayuda sería muy apreciada! ¡Gracias!
Mi código:
package main;
import java.lang.reflect.Field;
public class Tester {
public static void main(String args[]) throws Exception {
new Tester().reflectionTest();
}
public void reflectionTest() throws Exception {
Person person = new Person("John Doe", "555-123-4567", "Rover");
Field[] fields = person.getClass().getDeclaredFields();
for (Field field : fields) {
System.out.println("Field Name: " + field.getName());
System.out.println("Field Type: " + field.getType());
System.out.println("Field Value: " + field.get(person));
//The line above throws: Exception in thread "main" java.lang.IllegalAccessException: Class main.Tester can not access a member of class main.Tester$Person with modifiers "private final"
}
}
public class Person {
private final String name;
private final String phoneNumber;
private final String dogsName;
public Person(String name, String phoneNumber, String dogsName) {
this.name = name;
this.phoneNumber = phoneNumber;
this.dogsName = dogsName;
}
}
}
La salida:
run:
Field Name: name
Field Type: class java.lang.String
Exception in thread "main" java.lang.IllegalAccessException: Class main.Tester can not access a member of class main.Tester$Person with modifiers "private final"
at sun.reflect.Reflection.ensureMemberAccess(Reflection.java:95)
at java.lang.reflect.AccessibleObject.slowCheckMemberAccess(AccessibleObject.java:261)
at java.lang.reflect.AccessibleObject.checkAccess(AccessibleObject.java:253)
at java.lang.reflect.Field.doSecurityCheck(Field.java:983)
at java.lang.reflect.Field.getFieldAccessor(Field.java:927)
at java.lang.reflect.Field.get(Field.java:372)
at main.Tester.reflectionTest(Tester.java:17)
at main.Tester.main(Tester.java:8)
Java Result: 1
BUILD SUCCESSFUL (total time: 0 seconds)
Por defecto, no está permitido leer campos no públicos, sino simplemente invocando field.setAccessible(true);
permitirá el acceso. En otras palabras, tu código debería decir
for (Field field : fields) {
field.setAccessible(true);
....