Java循环⼀个对象的所有属性,并通过反射给这些属性赋值取
值
Java循环⼀个对象的所有属性,并通过反射给这些属性赋值/取值
说到循环遍历,最常见的遍历数组/列表、Map等。但是,在开发过程中,有时需要循环遍历⼀个对象的所有属性。遍历对象的属性该如何遍历呢?查了⼀下资料,需要⽤到⼀些反射的知识!
话不多说,先上代码
⾸先先定义⼀个测试对象 Test
public class Test {
private String aa;
private int bb;
private String cc;
public String dd;
public String getAa() {
return aa;
}
public void setAa(String aa) {
this.aa = aa;
}
public int getBb() {
return bb;
}
public void setBb(int bb) {
this.bb = bb;
}
public String getCc() {
return cc;
}
public void setCc(String cc) {
< = cc;
}
}
这个对象⾥分别有aa bb cc 三个私有属性,dd⼀个公有属性,接下来通过反射来获取这个对象的四个属性值
public static void main(String[] args) {
/**
* 返回Class 对象所表⽰的类或接⼝的所有可访问公共字段。
*/
Field[] f1=Fields();
System.out.println("Test类⾥⾯的公共字段属性的个数为:" +f1.length+"个,分别为:");
for(int i=0;i<f1.length;i++){
String attributeName=f1[i].getName();
System.out.println(attributeName);
}
/**
* 返回 Class 对象所表⽰的类或接⼝所声明的所有字段,
* 包括公共、保护、默认(包)访问和私有字段,但不包括继承的字段。
*/
Field[] f=DeclaredFields();
System.out.println("Test类⾥⾯的所有字段属性的个数为:"+f.length+"个,分别为:");
for(int i=0;i<f.length;i++){
String attributeName=f[i].getName();
System.out.println(attributeName);
}
}
运⾏main函数,输出如下:
Test类⾥⾯的公共字段属性的个数为:1个,分别为:
dd
Test类⾥⾯的所有字段属性的个数为:4个,分别为:
aa
bb
cc
dd
getFields()⽅法只能获取Test类⾥⾯的所有公有属性,getDeclaredFields()⽅法可获取Test类所有公有/私有属性。需要注意的是,如果Test 类继承了别的类,这两个⽅法都⽆法获取⽗类⾥⾯的属性的。
现在,已经获取到了Test类⾥⾯的所有属性名,然后通过这些属性名给这个类的实例赋值和取值操作。
先来给实例赋值,代码如下:
Test test=new Test();
//给test对象赋值
for(int i=0;i<f.length;i++){
//获取属相名
String attributeName=f[i].getName();
//将属性名的⾸字母变为⼤写,为执⾏set/get⽅法做准备
String methodName=attributeName.substring(0,1).toUpperCase()+attributeName.substring(1);
try{
//获取Test类当前属性的setXXX⽅法(私有和公有⽅法)
/*Method setMethod=DeclaredMethod("set"+methodName);*/
//获取Test类当前属性的setXXX⽅法(只能获取公有⽅法)
Method setMethod=Method("set"+methodName,String.class);
//执⾏该set⽅法
setMethod.invoke(test,attributeName+"⽅法赋值");
}catch (NoSuchMethodException e) {
try {
Method setMethod=Method("set"+methodName,int.class);
setMethod.invoke(test,123);
} catch (Exception e2) {
f[i].set(test,attributeName+"直接赋值");
}
}
}
如上代码,之前已经获取到了Test类⾥⾯的所有属性名,在这部分代码中,就可以通过属性名来获取
与之对应的set⽅法。需要注意的是,在上⾯代码中try-catch了两次,是因为在Test这个类中的属性的set⽅法的参数,有的是String类型,有的是int类型的,还有的属性是没有set⽅法的。第⼀次try是未了抓取所有参数类型不是String类型和不存在的set⽅法。第⼆次抓取的是参数不是int类型的和不存在的set⽅法。依次进⾏处理。除此之外,假如set⽅法的参数类型还有更多的类型的话,可以通过Filed类的getGenericType() 这个⽅法先判断类型,这个以后再做赘述。
接下来从实例中通过get⽅法来取值,代码如下:
//从test对象取值
for(int i=0;i<f.length;i++){
//获取属相名
String attributeName=f[i].getName();
//将属性名的⾸字母变为⼤写,为执⾏set/get⽅法做准备
String methodName=attributeName.substring(0,1).toUpperCase()+attributeName.substring(1);
Object result;
try{
//获取Test类当前属性的setXXX⽅法(私有和公有⽅法)
/*Method setMethod=DeclaredMethod("set"+methodName);*/
//获取Test类当前属性的setXXX⽅法(只能获取公有⽅法)
Method getMethod=Method("get"+methodName);
//执⾏该set⽅法
result=getMethod.invoke(test);
}catch(NoSuchMethodException e){
result=f[i].get(test);
}
System.out.println("属性:"+attributeName+"="+result);
}
这⾥的代码也try-catch⼀次,get⽅法不存在参数类型判断的,这⾥的try-catch只是为了抓取公有属性不存在get⽅法的情况以做相应的处理。
运⾏测试程序,输出结果如下:
属性:aa=aa⽅法赋值
属性:bb=123
属性:cc=cc⽅法赋值
属性:dd=dd直接赋值
最后附上完整的测试程序
public static void main(String[] args) throws Exception{
/**
* 返回Class 对象所表⽰的类或接⼝的所有可访问公共字段。
*/
Field[] f1=Fields();
System.out.println("Test类⾥⾯的公共字段属性的个数为:" +f1.length+"个,分别为:");
for(int i=0;i<f1.length;i++){
String attributeName=f1[i].getName();
System.out.println(attributeName);
}
/**
* 返回 Class 对象所表⽰的类或接⼝所声明的所有字段,
* 包括公共、保护、默认(包)访问和私有字段,但不包括继承的字段。
*/
java定义一维数组并赋值
Field[] f=DeclaredFields();
System.out.println("Test类⾥⾯的所有字段属性的个数为:"+f.length+"个,分别为:");
for(int i=0;i<f.length;i++){
String attributeName=f[i].getName();
System.out.println(attributeName);
}
Test test=new Test();
//给test对象赋值
for(int i=0;i<f.length;i++){
//获取属相名
String attributeName=f[i].getName();
/
/将属性名的⾸字母变为⼤写,为执⾏set/get⽅法做准备
String methodName=attributeName.substring(0,1).toUpperCase()+attributeName.substring(1); try{
//获取Test类当前属性的setXXX⽅法(私有和公有⽅法)
/*Method setMethod=DeclaredMethod("set"+methodName);*/
//获取Test类当前属性的setXXX⽅法(只能获取公有⽅法)
Method setMethod=Method("set"+methodName,String.class);
//执⾏该set⽅法
setMethod.invoke(test,attributeName+"⽅法赋值");
}catch (NoSuchMethodException e) {
try {
Method setMethod=Method("set"+methodName,int.class);
setMethod.invoke(test,123);
} catch (Exception e2) {
f[i].set(test,attributeName+"直接赋值");
}
}
}
//从test对象取值
for(int i=0;i<f.length;i++){
//获取属相名
String attributeName=f[i].getName();
//将属性名的⾸字母变为⼤写,为执⾏set/get⽅法做准备
String methodName=attributeName.substring(0,1).toUpperCase()+attributeName.substring(1); Object result;
try{
//获取Test类当前属性的setXXX⽅法(私有和公有⽅法)
/*Method setMethod=DeclaredMethod("set"+methodName);*/
//获取Test类当前属性的setXXX⽅法(只能获取公有⽅法)
Method getMethod=Method("get"+methodName);
//执⾏该set⽅法
result=getMethod.invoke(test);
}catch(NoSuchMethodException e){
result=f[i].get(test);
}
System.out.println("属性:"+attributeName+"="+result);
}
}
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论