函数参数不够,则 newInstance(Object[]) 将抛出异常。被实例化的类必须 包含具有给定签名的构造函数。
可以使用第一个方法 (newInstance(Class<T>)) 实例化拥有默认构造函数的任何类中的对象。 也可以使用第二个方法。通过传递参数类型及其各自参数中的值,将通过匹配构造函数来实现实例化。例 如,可以使用具有四个类型为 int 的参数的构造函数对 Rectangle 类进行实例化,使用的代码如下所示 :
Object[] params = { 1, 2, 100, 200 };
Class[] paramClazzes = { int.class, int.class, int.class, int.class };
Rectangle rectangle = ReflectionUtil.newInstance(
Rectangle.class, paramClazzes, params);
System.out.println(rectangle);
上面代码将产生以下输出。
java.awt.Rectangle[x=1,y=2,width=100,height=200]
反射实践(7)
时间:2011-08-09 Albert Attard
通过反射更改字段值
可以通过反射设置字段的值,其方式与读取它们的方式类似。在尝试设置值之前,设置该字段的可访 问性,这一点非常重要。因为如果不这样,将抛出一个异常。
field.setAccessible(true);
field.set(object, newValue);
我们可以轻松草拟一个可以设置其任何对象的值的方法,如以下实例所示。
public static void setFieldValue(Object object, String fieldName,
Object newValue) throws NoSuchFieldException,
IllegalArgumentException, IllegalAccessException {
Class<?> clazz = object.getClass();
Field field = clazz.getDeclaredField(fieldName);
field.setAccessible(true);
field.set(object, newValue);
}
该方法有一个缺陷,它只能从给定的类中检索字段。不包含继承的字段。可以使用以下方法快速解决 这个问题,该方法查找所需的 Field 的对象层次结构。
public static Field getDeclaredField(Object object, String name)
throws NoSuchFieldException {
Field field = null;
Class<?> clazz = object.getClass();
do {
try {
field = clazz.getDeclaredField(name);
} catch (Exception e) { }
} while (field == null & (clazz = clazz.getSuperclass()) != null);
if (field == null) {
throw new NoSuchFieldException();
}
return field;
}
该方法将返回具有给定名称的 Field(如果找到);否则它将抛出一个异常,表明该对象没有该字段 ,也没有继承该字段。它从给定类开始搜索,一直沿层次结构搜索,直到找到 Field 或者没有超级类可 用为止。
请注意,所有 Java 类都从 Object 类继承(直接或过渡)。您可能已经意识到, Object 类不从自 身继承。因此, Object 类没有超级类。
修改前面演示的方法 setFieldValue(Object, String, Object) 以适合这种情况。更改如下面粗体所 示。
public static void setFieldValue(Object object, String fieldName,
Object newValue) throws IllegalArgumentException,
IllegalAccessException, NoSuchFieldException {
Field field = getDeclaredField(object, fieldName);
field.setAccessible(true);
field.set(object, newValue);
}
让我们创建另一个名 Book 的类,该类扩展前面讨论的 Product 类,并应用目前我们所学到的内容。
package ria;
public class Book extends Product {
private String isbn;
//Getters and setters are omitted for shortness
}
反射实践(8)
时间:2011-08-09 Albert Attard
现在,使用 setFieldValue(Object, String, Object) 方法设置 Book 的 id |