data是Class MyType的ArrayList,如果仅使用field.get(object)
,则代码不会编译说未处理的异常。
当我运行它时,我无法访问私人成员。然后我将MyType
的所有成员字段更改为public。然后这段代码可行。但肯定有更好的获取数据的方法吗?
for (Object object : data)//get one object
{
ArrayList<Field> fields =
new ArrayList<Field>(Arrays.asList(object.getClass().getDeclaredFields()));//get all its fields
for(Field field : fields)
{
try {
System.out.println(field.get(object));//print its fields value
} catch (IllegalArgumentException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IllegalAccessException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
答案 0 :(得分:2)
使用Field.setAccessible(true)
允许访问私有字段。
try {
field.setAccessible(true);
System.out.println(field.get(object));//print its fields value
} catch (IllegalArgumentException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
答案 1 :(得分:1)
最干净的方法是创建一个接口并从中派生出来或从一个抽象的超类派生。在这两种情况下,编译器都知道构造。 您可以通过以下代码获得带反射的单个字段:
Method.class.getDeclaredField(name)
答案 2 :(得分:0)
您可以使用setAccessible(boolean)
,Field
和Method
上的Constructor
来访问调用者通常无法访问的非公开成员。这样做可以消除您的错误。
更标准化的方法是使用introspection。如果该类遵循JavaBean约定,那么您可以使用Introspector
和BeanInfo
来获取PropertyDescriptor
实例,这使您可以访问bean的公共读写方法(getter和setter) 。例如,这是一个示例bean:
public class JavaBean {
private boolean valid;
private String name;
private String label;
public boolean isValid() {
return valid;
}
public String getName() {
return name;
}
public String getLabel() {
return label;
}
public void setValid(boolean valid) {
this.valid = valid;
}
public void setName(String name) {
this.name = name;
}
public void setLabel(String label) {
this.label = label;
}
}
在此,我们声明了valid
,name
和label
属性。请注意,字段名称不用于确定属性的名称。相反,使用了get
/ is
和set
方法。另请注意,原始boolean
属性使用is
作为getter前缀。
然后使用内省:
Object unknownType = new JavaBean();
BeanInfo javaBeanInfo = Introspector.getBeanInfo(JavaBean.class);
for (PropertyDescriptor property : javaBeanInfo.getPropertyDescriptors()) {
System.out.println(property.getName());
}
这将打印(不一定按顺序):
class
valid
name
label
class
位于此处,因为所有类都存在getClass()
方法,因此class
被视为属性。
然后,您可以使用PropertyDescriptor.readMethod
和PropertyDescriptor.writeMethod
分别获取作为getter和setter的Method
个对象,然后使用Method.invoke
来获取和设置属性使用通常的反射API的给定对象的值。 PropertyDescriptor
还有一些其他信息,例如属性类型和属性名称。这是直接使用反射的替代方法。它还允许其他人覆盖BeanInfo
返回的Introspector
作为自定义实现。