反射就是通过类的字节码直接获取类的对象或各种信息
想一下类都有那些部分呢?
- field:
- 按类型
- 静态field
- 普通field
- 按权限
- 共有
- 私有
- method
- 静态
- 普通
- 公开
- 私有
- 构造器
- Anotation
或许还有什么东西,反正一句话:只要他有的我都能获取
下面具体找一找方法:
- 得到field:
//Field[] field = cla.getFields();//找到的只有public的field
//Field[] field = cla.getDeclaredFields();//得到所有的field
//通过名字得到field
//Field field = cla.getField(“text”);
//Field field = cla.getDeclaredField(“text”); - 得到field的属性
- 获取对象中field的值:
- public或protected权限
- 用方法直接取出
方法:
- field.get(obj)
- field.getInt(obj)
- ……
- private权限
- 先声明可访问
- field.setAccessible(true);
- 用方法取出(同上)
- 设置对象中field的值
- public或protected权限
- field.set(obj, “lala”);
- field.setInt(obj, i);
- …….
- private权限
- 先声明可访问
- field.setAccessible(true);
- 设置值(同上)
- 其他
- field.getName()
- field.getType()
- 得到方法相关方法:
- 构造方法及相关属性
- con.newInstance(initargs)
- con.getParameterTypes()
- con.getDeclaringClass()
- con.getName() //得到构造方法的类名(String)
- con.getParameters()
- con.getParameterCount()
- con.toString() //或是直接输出con,打印出构造方法原型
- 普通方法
- cla.getDeclaredMethod(methodName, null);
只能得到本类的方法(包括私有和公有),但不能得到父类的任何方法
如果是private方法,还需要m.setAccessible(true);设置可访问 - cla.getMethod(methodName, null);
这货只能得到public方法(包括本类和父类),但不能得到private和protected方法
思考怎么获取父类的私有方法?
- 普通方法的相关属性
- m.invoke(obj, args); //调用方法,参一为调用对象,参二为可变参数
- m.toString()//打印出方法声明
- m.getReturnType()//返回值
- m.getParameterCount()//参数个数
- m.getName()//方法名
- m.getClass()//Object类的方法,返回对象的Class对象
- m.getDeclaringClass()//返回方法的声明类Class对象
- m.getParameters();//Parameter[]//得到所有的参数
- m.getParameterTypes(); //得到所有的参数类型
- m.toString() //或是直接输出m,打印出方法原型
- 方法参数类Parameter
- 没什么有价值的方法:p.getType();//得到参数的类型
- Class对象,类的字节码
除了可获得方法,field,还能得到其父类,得到类名,包名
class.isArray(); //通过字节码判断对象是否是数组 - 数组的反射:
- 相同维度,相同类型的数组的字节码相同
- 数组的父类是Object
- Array类用于数组的反射操作(都是静态方法)
- setXXX(Object array, int index, T value)
- getXXX(Object array, int index)
- getLength(Object array)
- Array.newInstance(Class type, int length);
- 此方法返回一个对象(数组对象),类型强转就行
特殊情况:
jdk1.4中没有可变参数,为了向上兼容,在method.invoke(obj, 数组);
如果传入的数组,编译器就会把数组中的每个元素当成多个参数
可是如果参数真的是数组,那就麻烦了
解决办法:
- 把数组转为Object对象,(Object)Array
- 把数组放到Object数组中,new Object[]{Array}