Java:反射
·
1.反射的概述
什么是反射?
反射允许对成员变量,成员方法和构造方法的信息进行编程访问


先学习如何获取字节码文件的对象,再学习如何从字节码文件里面获取到字段、构造方法、成员方法,然后再解刨获取到里面的每一个信息
2.获取class对象的三种方式
①Class.forName("全类名");
②类名.class
③对象.getClass();




3.反射获取构造方法

| 方法 | 说明 |
|---|---|
| Constructor<?>[ ] getConstructors() | 返回所有公共构造方法对象的数组 |
| Constructor<?>[ ]getDeclaredConstructors() | 返回所有构造方法对象的数组 |
| Constructor<T> getConstructor(Class<?>..parameterTypes) | 返回单个公共构造方法对象 |
| Constructor<T> getDeclaredConstructor(Class<?>..parameterTypes) | 返回单个构造方法对象 |
| 方法 | 说明 |
|---|---|
| T newInstance(Object...initargs) | 根据指定的构造方法创建对象 |
| setAccessible(boolean flag) | 设置为true,表示取消访问检查 |

package com.dan.myreflect2;
import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Parameter;
public class MyReflectDemo2 {
public static void main(String[] args) throws ClassNotFoundException, NoSuchMethodException, InvocationTargetException, InstantiationException, IllegalAccessException {
/**
*Constructor<?>[ ] getConstructors() 返回所有公共构造方法对象的数组
* Constructor<?>[ ]getDeclaredConstructors() 返回所有构造方法对象的数组
* Constructor<T> getConstructor(Class<?>..parameterTypes) 返回单个公共构造方法对象
* Constructor<T> getDeclaredConstructor(Class<?>..parameterTypes) 返回单个构造方法对象
*
* T newInstance(Object...initargs) 根据指定的构造方法创建对象
* setAccessible(boolean flag) 设置为true,表示取消访问检查
*/
//1.获取class字节码文件对象
Class clazz = Class.forName("com.dan.myreflect2.Student");
//2.获取构造方法
Constructor[] cons = clazz.getConstructors();
for (Constructor con : cons) {
System.out.println(con);
}
System.out.println("-----------");
Constructor[] cons2 = clazz.getDeclaredConstructors();
for (Constructor con : cons2) {
System.out.println(con);
}
System.out.println("-----------");
Constructor con3 = clazz.getConstructor();
System.out.println(con3);
System.out.println("-----------");
Constructor con4 = clazz.getDeclaredConstructor(int.class);
System.out.println(con4);
System.out.println("-----------");
Constructor con5 = clazz.getDeclaredConstructor(String.class,int.class);
System.out.println(con5);
System.out.println("-----------");
int modifiers = con5.getModifiers();
System.out.println(modifiers);
System.out.println("-----------");
Parameter[] parameters = con5.getParameters();
for (Parameter parameter : parameters) {
System.out.println(parameter);
}
System.out.println("-----------");
//暴力反射:表示临时取消权限校验
con5.setAccessible(true);
Student stu = (Student) con5.newInstance("张三", 21);
System.out.println(stu);
}
}


4.反射获取成员变量
| 方法 | 说明 |
|---|---|
| Field[ ] getFields() | 返回所有公共成员变量对象的数组 |
| Field[ ]getDeclaredFields() | 返回所有成员变量对象的数组 |
| Field getField(String name) | 返回单个公共成员变量对象 |
| Field getDeclaredField(String name) | 返回单个成员变量对象 |
| 方法 | 说明 |
|---|---|
| void set(Object obj, Object value) | 赋值 |
| Object get(Object obj) | 获取值 |
package com.dan.myreflect3;
import java.lang.reflect.Field;
public class MyReflectDemo3 {
public static void main(String[] args) throws ClassNotFoundException, NoSuchFieldException, IllegalAccessException {
/**
*Field[ ] getFields() 返回所有公共成员变量对象的数组
* Field[ ]getDeclaredFields() 返回所有成员变量对象的数组
* Field getField(String name) 返回单个公共成员变量对象
* Field getDeclaredField(String name) 返回单个成员变量对象
*
* void set(Object obj, Object value) 赋值
* Object get(Object obj) 获取值
*/
//1.获取class字节码文件的对象
Class clazz = Class.forName("com.dan.myreflect3.Student");
//2.获取所有的成员变量
Field[] fields = clazz.getFields();
for (Field field : fields) {
System.out.println(field);
}
System.out.println("--------");
//3.获取单个的成员变量
Field name = clazz.getDeclaredField("name");
System.out.println(name);
System.out.println("--------");
//获取权限修饰符
int modifiers = name.getModifiers();
System.out.println(modifiers);
System.out.println("--------");
//获取成员变量的名字
String n = name.getName();
System.out.println(n);
System.out.println("--------");
//获取成员变量的类型
Class<?> type = name.getType();
System.out.println(type);
System.out.println("--------");
//获取成员变量记录的值
Student s = new Student("zhangsan",23,"男");
name.setAccessible(true);
Object value = name.get(s);
System.out.println(value);
System.out.println("---------");
//修改对象里面记录的值
name.set(s,"lisi");
System.out.println(s);
}
}


5.反射获取成员方法
| 方法 | 说明 |
|---|---|
| Method[ ]getMethods() | 返回所有公共成员方法对象的数组,包括继承的 |
| Method[ ]getDeclaredMethods() | 返回所有成员方法对象的数组,不包括继承的 |
| Method getMethod(String name,Class<?>...parameterTypes) | 返回单个公共成员方法对象 |
| Method getDeclaredMethod(String name, Clas<?>..parameterTypes) | 返回单个成员方法对象 |
Method类中用于创建对象的方法
Object invoke(Object obj, Object.. args):运行方法
参数一:用obj对象调用该方法
参数二:调用方法的传递的参数(如果没有就不写)
返回值:方法的返回值(如果没有就不写)
package com.dan.myreflect4;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.lang.reflect.Parameter;
public class MyReflectDemo4 {
public static void main(String[] args) throws ClassNotFoundException, NoSuchMethodException, InvocationTargetException, IllegalAccessException {
//1.获取class字节码文件对象
Class<?> clazz = Class.forName("com.dan.myreflect4.Student");
//2.获取里面所有的方法对象(包含父类中的所有的公共方法)
Method[] methods = clazz.getMethods();
for (Method method : methods) {
System.out.println(method);
}
System.out.println("----------");
//获取里面的所有方法对象(不能获取父类的方法对象)
Method[] methods2 = clazz.getDeclaredMethods();
for (Method method : methods2) {
System.out.println(method);
}
System.out.println("----------");
//获取指定的单一方法
Method m = clazz.getDeclaredMethod("eat",String.class);
System.out.println(m);
System.out.println("----------");
//获取方法的修饰符
int modifiers = m.getModifiers();
System.out.println(modifiers);
System.out.println("----------");
//获取方法的名字
String name = m.getName();
System.out.println(name);
System.out.println("----------");
//获取方法的形参
Parameter[] parameters = m.getParameters();
for (Parameter parameter : parameters) {
System.out.println(parameter);
}
System.out.println("----------");
//获取方法的抛出异常
Class<?>[] exceptionTypes = m.getExceptionTypes();
for (Class<?> exceptionType : exceptionTypes) {
System.out.println(exceptionType);
}
System.out.println("----------");
//方法运行
Student s = new Student();
m.setAccessible(true);
//参数一:s表示方法的调用者
//参数二:“汉堡”表示在调用方法的时候传递的实际参数
m.invoke(s,"汉堡");
}
}


6.反射的作用
①获取一个类里面所有的信息,获取到了之后,再执行其他的业务逻辑
②结合配置文件,动态的创建对象并调用方法
更多推荐




所有评论(0)