Java反射分析对象的Fields

package chapter05.ObjectAnalyzer;

import java.lang.reflect.AccessibleObject;
import java.lang.reflect.Array;
import java.lang.reflect.Field;
import java.lang.reflect.Modifier;
import java.util.ArrayList;

public class ObjectAnalyzer {
	private ArrayList<Object> visited=new ArrayList<>();
	public String toString(Object obj){
		if(obj==null)return "null";
		if(visited.contains(obj))return ",,,";
		visited.add(obj);
		Class cl=obj.getClass();                    
		if(cl==String.class)return (String)obj;
		if(cl.isArray()){							
			  String r=cl.getComponentType()+"[]{"; 
			  for(int i=0;i<Array.getLength(obj);i++){
				  if(i>0)r+=",";
				  Object val=Array.get(obj, i);
				  if(cl.getComponentType().isPrimitive()){
					  r+=val;
				  }
				  else{
					  r+=toString(val);                            //!!!
				  }
			  }
			  return r+"};";
		}
		String r=cl.getName();
		do{
			r+="[";
			Field[] fields=cl.getDeclaredFields();            
			AccessibleObject.setAccessible(fields, true);    
			for(Field element:fields){
				if(!Modifier.isStatic(element.getModifiers())){
					if(!r.endsWith("["))r+=",";
					r+=element.getName()+"=";
					try{
						Class t=element.getType();              
						Object val=element.get(obj);            
						if(t.isPrimitive())r+=val;
						else r+=toString(val);                  //!!!
					}catch(Exception e){
						e.printStackTrace();
					}
				}
			}
			r+="]";
			cl.getSuperclass();
		}while(cl!=null);
		return r;
	}
}

再来段测试

package chapter05.ObjectAnalyzer;

import java.util.ArrayList;

public class ObjectAnalyzerTest {
	public static void main(String[] args){
		ArrayList<Integer> squares=new ArrayList<>();
		for(int i=1;i<=5;i++){
			squares.add(i*i);
		}
		System.out.println(new ObjectAnalyzer().toString(squares));
	}
}
这是coreJava上一段关于利用反射分析基本类型数组和基本类型泛型数组的一段代码,首先我们明确几个问题:

1.泛型数组不是数组,2.自己编写的类,做成数组后,是数组,

如下:

ArrayList<Integer> squares=new ArrayList<>();
		for(int i=1;i<=5;i++){
			squares.add(i*i);
		}
		System.out.println(squares.getClass().isArray());//返回false

		Employee[] xy=new Employee[2];
		Employee x=new Employee("asan",35000.0);
		Employee y=new Employee("asi",45000.0);
		System.out.println(xy.getClass().isArray()); //返回true

然后再理清:

				  if(cl.getComponentType().isPrimitive()){
					  r+=val;
				  }
				  else{
					  r+=toString(val);//这里前面是有指代
				  
						if(t.isPrimitive())r+=val;
						else r+=toString(val); 
第一个即是,如果数组是基本类型,则将里面元素一一打印,否则返回null(我的理解,我试过,只要数组不是基本数据类型或者String类型,则会返回数组元素都是null,那么这个对象分析器是不是太弱了?)

第二与第一个有所不同,如示例返回的结果:
java.util.ArrayList[elementData=class java.lang.Object[]{java.lang.Integer[value=1][][],java.lang.Integer[value=4][][],java.lang.Integer[value=9][][],java.lang.Integer[value=16][][],java.lang.Integer[value=25][][],null,null,null,null,null};,size=5][modCount=5][][]

首先我们剥去
if(!r.endsWith("["))r+=",";
我们会看到
java.util.ArrayList[elementData=class java.lang.Object[]{java.lang.Integer[value=1][][],java.lang.Integer[value=4][][],java.lang.Integer[value=9][][],java.lang.Integer[value=16][][],java.lang.Integer[value=25][][],null,null,null,null,null};size=5][modCount=5][][]

如果剥去else分支,则:
java.util.ArrayList[elementData=,size=5][modCount=5][][]

剥去if分支可以看到:
java.util.ArrayList[elementData=class java.lang.Object[]{java.lang.Integer[value=,,,][][],java.lang.Integer[value=,,,][][],java.lang.Integer[value=,,,][][],java.lang.Integer[value=,,,][][],java.lang.Integer[value=,,,][][],null,null,null,null,null};,size=java.lang.Integer[value=,,,][][]][modCount=,,,][][]

好了

后面跟着三个[][]很好理解,即是ArrayList共有三个超类
关于这个泛型数组中第一个超类,中有一个modCount的 Field,这个Field name 是modCount,是指这个泛型数组被修改的次数!

问题是:

去掉else后,发现关于非基本数据类型的Feild的描述没有了,那么是不是if的分支就是在打印两个5呢?可见不是的,我们去掉if分支后,发现所有的基本数据类型都不见了,这点就不能解释了???

去掉逗号后, 仅仅在一个个中括号内多了一个“,”;意思即是ArrayList<Integer> squares这个泛型数组有两个Field,一个是element,另一个是size;这点在API中查不到???



我们再剥去

if(!Modifier.isStatic(element.getModifiers())){

得到下述结果:

java.util.ArrayList[serialVersionUID=8683452581122892189,DEFAULT_CAPACITY=10,EMPTY_ELEMENTDATA=class java.lang.Object[]{};,elementData=class java.lang.Object[]{java.lang.Integer[MIN_VALUE=-2147483648,MAX_VALUE=2147483647,TYPE=java.lang.Class[ANNOTATION=8192,ENUM=16384,SYNTHETIC=4096,cachedConstructor=null,newInstanceCallerCache=null,name=null,allPermDomain=null,useCaches=true,declaredFields=null,publicFields=null,declaredMethods=null,publicMethods=null,declaredConstructors=null,publicConstructors=null,declaredPublicFields=null,declaredPublicMethods=null,classRedefinedCount=0,lastRedefinedCount=0,genericInfo=null,serialVersionUID=3206093459760846163,serialPersistentFields=class java.io.ObjectStreamField[]{};,reflectionFactory=sun.reflect.ReflectionFactory[initted=true,reflectionFactoryAccessPerm=java.lang.RuntimePermission[serialVersionUID=7399184964622342223][serialVersionUID=6279438298436773498,wildcard=false,path=reflectionFactoryAccess,exitVM=false][serialVersionUID=-5636570222231596674,name=,,,][],soleInstance=,,,,langReflectAccess=java.lang.reflect.ReflectAccess[][],noInflation=false,inflationThreshold=15][],initted=true,enumConstants=null,enumConstantDirectory=null,annotations=null,declaredAnnotations=null,annotationType=null,classValueMap=null][],digits=char[]{0,1,2,3,4,5,6,7,8,9,a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z};,DigitTens=char[]{0,0,0,0,0,0,0,0,0,0,1,1,1,1,1,1,1,1,1,1,2,2,2,2,2,2,2,2,2,2,3,3,3,3,3,3,3,3,3,3,4,4,4,4,4,4,4,4,4,4,5,5,5,5,5,5,5,5,5,5,6,6,6,6,6,6,6,6,6,6,7,7,7,7,7,7,7,7,7,7,8,8,8,8,8,8,8,8,8,8,9,9,9,9,9,9,9,9,9,9};,DigitOnes=char[]{0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9};,sizeTable=int[]{9,99,999,9999,99999,999999,9999999,99999999,999999999,2147483647};,value=1,SIZE=32,serialVersionUID=1360826667806852920,$assertionsDisabled=true][serialVersionUID=-8742448824652078965][],java.lang.Integer[MIN_VALUE=-2147483648,MAX_VALUE=2147483647,TYPE=java.lang.Class[ANNOTATION=8192,ENUM=16384,SYNTHETIC=4096,cachedConstructor=null,newInstanceCallerCache=null,name=int,allPermDomain=null,useCaches=true,declaredFields=null,publicFields=null,declaredMethods=null,publicMethods=null,declaredConstructors=null,publicConstructors=null,declaredPublicFields=null,declaredPublicMethods=null,classRedefinedCount=0,lastRedefinedCount=0,genericInfo=null,serialVersionUID=3206093459760846163,serialPersistentFields=class java.io.ObjectStreamField[]{};,reflectionFactory=sun.reflect.ReflectionFactory[initted=true,reflectionFactoryAccessPerm=java.lang.RuntimePermission[serialVersionUID=7399184964622342223][serialVersionUID=6279438298436773498,wildcard=false,path=reflectionFactoryAccess,exitVM=false][serialVersionUID=-5636570222231596674,name=,,,][],soleInstance=,,,,langReflectAccess=java.lang.reflect.ReflectAccess[][],noInflation=false,inflationThreshold=15][],initted=true,enumConstants=null,enumConstantDirectory=null,annotations=null,declaredAnnotations=null,annotationType=null,classValueMap=null][],digits=char[]{0,1,2,3,4,5,6,7,8,9,a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z};,DigitTens=char[]{0,0,0,0,0,0,0,0,0,0,1,1,1,1,1,1,1,1,1,1,2,2,2,2,2,2,2,2,2,2,3,3,3,3,3,3,3,3,3,3,4,4,4,4,4,4,4,4,4,4,5,5,5,5,5,5,5,5,5,5,6,6,6,6,6,6,6,6,6,6,7,7,7,7,7,7,7,7,7,7,8,8,8,8,8,8,8,8,8,8,9,9,9,9,9,9,9,9,9,9};,DigitOnes=char[]{0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9};,sizeTable=int[]{9,99,999,9999,99999,999999,9999999,99999999,999999999,2147483647};,value=4,SIZE=32,serialVersionUID=1360826667806852920,$assertionsDisabled=true][serialVersionUID=-8742448824652078965][],java.lang.Integer[MIN_VALUE=-2147483648,MAX_VALUE=2147483647,TYPE=java.lang.Class[ANNOTATION=8192,ENUM=16384,SYNTHETIC=4096,cachedConstructor=null,newInstanceCallerCache=null,name=int,allPermDomain=null,useCaches=true,declaredFields=null,publicFields=null,declaredMethods=null,publicMethods=null,declaredConstructors=null,publicConstructors=null,declaredPublicFields=null,declaredPublicMethods=null,classRedefinedCount=0,lastRedefinedCount=0,genericInfo=null,serialVersionUID=3206093459760846163,serialPersistentFields=class java.io.ObjectStreamField[]{};,reflectionFactory=sun.reflect.ReflectionFactory[initted=true,reflectionFactoryAccessPerm=java.lang.RuntimePermission[serialVersionUID=7399184964622342223][serialVersionUID=6279438298436773498,wildcard=false,path=reflectionFactoryAccess,exitVM=false][serialVersionUID=-5636570222231596674,name=,,,][],soleInstance=,,,,langReflectAccess=java.lang.reflect.ReflectAccess[][],noInflation=false,inflationThreshold=15][],initted=true,enumConstants=null,enumConstantDirectory=null,annotations=null,declaredAnnotations=null,annotationType=null,classValueMap=null][],digits=char[]{0,1,2,3,4,5,6,7,8,9,a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z};,DigitTens=char[]{0,0,0,0,0,0,0,0,0,0,1,1,1,1,1,1,1,1,1,1,2,2,2,2,2,2,2,2,2,2,3,3,3,3,3,3,3,3,3,3,4,4,4,4,4,4,4,4,4,4,5,5,5,5,5,5,5,5,5,5,6,6,6,6,6,6,6,6,6,6,7,7,7,7,7,7,7,7,7,7,8,8,8,8,8,8,8,8,8,8,9,9,9,9,9,9,9,9,9,9};,DigitOnes=char[]{0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9};,sizeTable=int[]{9,99,999,9999,99999,999999,9999999,99999999,999999999,2147483647};,value=9,SIZE=32,serialVersionUID=1360826667806852920,$assertionsDisabled=true][serialVersionUID=-8742448824652078965][],java.lang.Integer[MIN_VALUE=-2147483648,MAX_VALUE=2147483647,TYPE=java.lang.Class[ANNOTATION=8192,ENUM=16384,SYNTHETIC=4096,cachedConstructor=null,newInstanceCallerCache=null,name=int,allPermDomain=null,useCaches=true,declaredFields=null,publicFields=null,declaredMethods=null,publicMethods=null,declaredConstructors=null,publicConstructors=null,declaredPublicFields=null,declaredPublicMethods=null,classRedefinedCount=0,lastRedefinedCount=0,genericInfo=null,serialVersionUID=3206093459760846163,serialPersistentFields=class java.io.ObjectStreamField[]{};,reflectionFactory=sun.reflect.ReflectionFactory[initted=true,reflectionFactoryAccessPerm=java.lang.RuntimePermission[serialVersionUID=7399184964622342223][serialVersionUID=6279438298436773498,wildcard=false,path=reflectionFactoryAccess,exitVM=false][serialVersionUID=-5636570222231596674,name=,,,][],soleInstance=,,,,langReflectAccess=java.lang.reflect.ReflectAccess[][],noInflation=false,inflationThreshold=15][],initted=true,enumConstants=null,enumConstantDirectory=null,annotations=null,declaredAnnotations=null,annotationType=null,classValueMap=null][],digits=char[]{0,1,2,3,4,5,6,7,8,9,a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z};,DigitTens=char[]{0,0,0,0,0,0,0,0,0,0,1,1,1,1,1,1,1,1,1,1,2,2,2,2,2,2,2,2,2,2,3,3,3,3,3,3,3,3,3,3,4,4,4,4,4,4,4,4,4,4,5,5,5,5,5,5,5,5,5,5,6,6,6,6,6,6,6,6,6,6,7,7,7,7,7,7,7,7,7,7,8,8,8,8,8,8,8,8,8,8,9,9,9,9,9,9,9,9,9,9};,DigitOnes=char[]{0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9};,sizeTable=int[]{9,99,999,9999,99999,999999,9999999,99999999,999999999,2147483647};,value=16,SIZE=32,serialVersionUID=1360826667806852920,$assertionsDisabled=true][serialVersionUID=-8742448824652078965][],java.lang.Integer[MIN_VALUE=-2147483648,MAX_VALUE=2147483647,TYPE=java.lang.Class[ANNOTATION=8192,ENUM=16384,SYNTHETIC=4096,cachedConstructor=null,newInstanceCallerCache=null,name=int,allPermDomain=null,useCaches=true,declaredFields=null,publicFields=null,declaredMethods=null,publicMethods=null,declaredConstructors=null,publicConstructors=null,declaredPublicFields=null,declaredPublicMethods=null,classRedefinedCount=0,lastRedefinedCount=0,genericInfo=null,serialVersionUID=3206093459760846163,serialPersistentFields=class java.io.ObjectStreamField[]{};,reflectionFactory=sun.reflect.ReflectionFactory[initted=true,reflectionFactoryAccessPerm=java.lang.RuntimePermission[serialVersionUID=7399184964622342223][serialVersionUID=6279438298436773498,wildcard=false,path=reflectionFactoryAccess,exitVM=false][serialVersionUID=-5636570222231596674,name=,,,][],soleInstance=,,,,langReflectAccess=java.lang.reflect.ReflectAccess[][],noInflation=false,inflationThreshold=15][],initted=true,enumConstants=null,enumConstantDirectory=null,annotations=null,declaredAnnotations=null,annotationType=null,classValueMap=null][],digits=char[]{0,1,2,3,4,5,6,7,8,9,a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z};,DigitTens=char[]{0,0,0,0,0,0,0,0,0,0,1,1,1,1,1,1,1,1,1,1,2,2,2,2,2,2,2,2,2,2,3,3,3,3,3,3,3,3,3,3,4,4,4,4,4,4,4,4,4,4,5,5,5,5,5,5,5,5,5,5,6,6,6,6,6,6,6,6,6,6,7,7,7,7,7,7,7,7,7,7,8,8,8,8,8,8,8,8,8,8,9,9,9,9,9,9,9,9,9,9};,DigitOnes=char[]{0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9,0,1,2,3,4,5,6,7,8,9};,sizeTable=int[]{9,99,999,9999,99999,999999,9999999,99999999,999999999,2147483647};,value=25,SIZE=32,serialVersionUID=1360826667806852920,$assertionsDisabled=true][serialVersionUID=-8742448824652078965][],null,null,null,null,null};,size=5,MAX_ARRAY_SIZE=2147483639][modCount=5][MAX_ARRAY_SIZE=2147483639][]

问题大了,出现了很多静态的Field:

但是我们在API文档中完全查不到踪影???

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值