I’ve been playing around with reflection in Java… and I’m a little bit baffled.
I was hoping that the program below would allow me to change the value of a public member variable within a class. However, I receive an IllegalArgumentException. Any ideas?
public class ColinTest {
public String msg = "fail";
public ColinTest() { }
public static void main(String args[]) throws Exception {
ColinTest test = new ColinTest();
Class c = test.getClass();
Field[] decfields = c.getDeclaredFields();
decfields[0].set("msg", "success");
System.out.println(ColinTest.msg)
}
}
I receive this message –
Exception in thread "main" java.lang.IllegalArgumentException
at sun.reflect.UnsafeFieldAccessorImpl.ensureObj(UnsafeFieldAccessorImpl.java:37)
at sun.reflect.UnsafeObjectFieldAccessorImpl.set(UnsafeObjectFieldAccessorImpl.java:57)
at java.lang.reflect.Field.set(Field.java:656)
at ColinTest.main(ColinTest.java:44)
Thanks.
The first argument of the
Field.setmethod should be the object which you are reflecting on.Should read:
Furthermore, the final
System.out.printlncall should refer to thetestobject rather than the classColinTest, as I presume the intention is to output the contents of thetest.msgfield.Update
As pointed out by toolkit and Chris, the
Class.getDeclaredFieldmethod can be used to specify the name of the field in order to retrieve it:Then, the
setmethod of themsgFieldcan be invoked as:This way has its benefit, as already pointed out by toolkit, if there are more fields added to the object, the order of the fields that are returned by
Class.getDeclaredFieldsmay not necessarily return the fieldmsgas the first element of the array. Depending on the order of the returned array to be a certain way may cause problems when changes are made to the class.Therefore, it would probably be a better idea to use
getDeclaredFieldand declare the name of the desired field.