Java是面向对象的编程语言,万物皆对象,反射技术就是把类声明、类中的字段声明、方法声明、构造函数声明等都看成是对象,从而可以把类中的各个部分拆解出来单独处理,反射技术主要用来编写通用功能,平时编程使用并不多。
反射技术所包含的类的含义非常简洁直观:
Class → 类声明
Constructor → 构造函数声明
Field → 字段声明
Method → 方法声明
抽象的地方在于通过反射类的对象访问普通对象的内容,其实这也算是另一种访问方式,和平时的访问方式时等价的。
- Java反射的知识结构图
- Class
一个Class对象表示一个类声明,通过Class对象可以获得该类声明的有关信息,比如类名、父类、类中的字段、类中的方法等。Class对象在.class文件被加载到内存时创建。
主要有三种方式获得一个类声明对应的Class对象
对象.getClass() 类名.class Class.forName("全类名")
Class的主要方法
String getSimpleName() //获得类的简单名称 String getName() //获取全类名 Class getSuperclass() //获得父类的Class对象 boolean isArray() //判断该类是否是数组 Object newInstance() //调用该类的无参构造函数创建该类对象 Constructors getConstructors() //获得所有的public构造函数 Constructors getConstructor(paramTypes) //获得指定参数类型的public构造函数 Field[] getFields() //获得所有的public字段,包括父类的 Field getField(name) //获得指定名称的public字段,包括父类的 Method[] getMethods() //获得所有的public方法,包括父类的 Method getMethod(name, paramTypes) //获得指定名称和参数类型的public方法,包括父类的 Constructors getDeclaredConstructors() //获得本类声明的所有构造函数 Constructors getDeclaredConstructor(paramTypes) //获得本类声明的所有指定参数类型的构造函数 Field[] getDeclaredFields() //获得本类声明的所有字段 Field getDeclaredField(name) //获得本类声明的指定名称的字段 Method[] getDeclaredMethods() //获得本类声明的所有方法 Method getDeclaredMethod(name, paramTypes) //获得本类声明的所有指定参数类型的方法
- Constructor
Constructor表示构造函数声明,一个Constructor对象就表示一个普通类的构造函数,既然表示一个构造函数,当然可以用来创建该普通类的对象:
Object obj = constructor.newInstance(initargs);
其实Class的newInstance()内部就是调用Constructor的newInstance()来创建对象的
- Field
Field表示字段声明,一个Field对象就表示一个普通类的字段,既然表示一个字段,当然可以用来获取普通对象中该字段的值,也可以给该字段赋值
field.get(obj); //获得obj对象中该字段的值 field.set(obj, newValue); //给obj对象中该字段赋值
如果Field对象表示的是private字段,可能需要调用field.setAccessible(true) 才能访问该字段
其实debug模式执行程序时看到的对象的字段值都是通过Field拿到的
- Method
Method表示方法声明,一个Method对象就表示一个普通类的方法,既然表示一个方法,当然就可以调用这个方法:
//假如method表示add方法 method.invoke(obj, num1, num2); //使用obj对象调用该add方法 // 等价于obj.add(num1,num2)