Получить личное поле с помощью отражения, в Java - PullRequest
0 голосов
/ 21 апреля 2020

У меня есть класс Java с именем "MyClass" с закрытым атрибутом типа "AnotherClass". MyClass имеет приватный конструктор, а "AnotherClass" имеет конструктор publi c. «AnotherClass» также имеет частное поле String «значение», которое инициализируется в конструкторе. Я хочу получить доступ в классе "Main" к этой строке.

Первый класс:

public class MyClass {
    private AnotherClass obj;

    private MyClass() {
        obj = new AnotherClass();
    }
}

Второй класс:

public class AnotherClass {
    private String value;

    public AnotherClass() {
        value = "You got the private value!";
    }
}

Основной класс:

public class Main {

    static String name;
    static AnotherClass obj;

    public static void main(String[] args) throws Exception {
        Class myClass;
        myClass = Class.forName("main.MyClass");
        Constructor<MyClass>[] constructors = myClass
            .getDeclaredConstructors();
        for (Constructor c : constructors) {
            if (c.getParameters().length == 0) {
                c.setAccessible(true);
                MyClass myCls= (MyClass) c.newInstance();
                Field myObjField = myClass
                    .getDeclaredField("obj");
                myObjField.setAccessible(true);
                obj = (AnotherClass) myObjField.get(myCls);

                // If "value" is public, the program prints "You got the private value!"
                // So "obj" is returned correctly, via reflection
                // name = obj.value; 
                // System.out.println(name); 

                // Now I want to get the field "value" of "obj"
                Field myStringField = obj.getClass().getDeclaredField("value");
                myStringField.setAccessible(true);

                // This line throws an exception
                name = (String) myStringField.get(obj.getClass());

                System.out.println(name); 
            }
        }
    }
}

Я ожидаю увидеть в консоль «Вы получили личное значение!», но программа выдает исключение:

Exception in thread "main" java.lang.IllegalArgumentException: Can not set java.lang.String field main.AnotherClass.value to java.lang.Class

Итак, я хочу получить личное поле «значение», не изменяя «MyClass» и «AnotherClass» и без вызова конструктора publi c из AnotherClass непосредственно в main (). Я хочу получить значение из "obj".

1 Ответ

1 голос
/ 21 апреля 2020

Измените эту строку

name = (String) myStringField.get(obj.getClass());

на эту

name = (String) myStringField.get(obj);

Для метода get требуется объект для доступа к полю (если это не поле stati c) *

...