反射
一、前言
反射是一种动态依赖机制,其作为各种 java 框架的核心,在 java 中具有举足轻重的地位。集多身优点的它,也因为动态加载而会损耗一定的性能。
其基本使用步骤可分为
- 1.获取 Class 对象
- 1.1使用 Class 对象获取 file(字段) 对象 对字段进行操作
- 1.2使用 Class 对象获取 method(方法) 对象 对方法进行调用。
- 1.3使用 Class 对象获取 constructor 对象对构造器进行调用。
下面来详细说每个步骤的使用方法
一、获取 Class 对象
从大维度上看,获取 Class 对象是从 4 个基本维度出发。
- 代码阶段
- ==Class.forName(“全路径”)==
- 前提:
- 已知一个类的全类名
- 类是否会被加载 –>是
- 场景
- 配置文件
- 类加载阶段
- ==类名.class==
- 类是否会被加载 –>否
- 场景
- 传参
- 运行阶段
- ==对象.class==
- 使用加载器
- 对象.getClass.getClassLoader() –》使用类的加载器的load方法进行类的加载
- 基本数据类型获得 Class
- 基本数据类型.class
- 基本数据类型的==包装类==
- 包装类.TYPE
二、常用方法
1.Class类
- static Class forName(String name)
- 返回指定类名 name 的 Class 对象
- Object newInstance
- 调用缺省构造函数,返回该 Class 对象的一个实例
- String getName()
- 返回此 Class 对象所表示的实体(类、接口、数组类、基本数据类型等)名称
- Class[] getInterfaces()
- 获取此 Class 对象的接口
- ClassLoader getClassLoader()
- 获取该类的类构造器
- Class getSuperclass()
- 返回表示此 Class 所表示的实体的类的 ==超类的Class==
- Constructor[] getConstructors()
- 返回一个包含本类构造器的数组
- Field[] getDeclaredFields()
- 返回 Field 对象的一个数组
- Method getMethod(String name, Class… paramTypes)
- 返回一个 Method 对象, name为方法名,方法的形参类型的 Class 对像
2.Method
额外的补充
类名.class 获取 Class 对象时,该类是否加载的问题。
使用 ==类名.class获取 Class==不会使 该类被加载,jvm 只会对其进行校验。只有在代码中真正用到了类。比如通过反设调用方法或创建对象,那么在这种情况下该类就会被加载。
例如1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20System.out.println(nte.class);
// System.out.println(nte.age);
Class<nte> nteClass = nte.class;
Method hi = nteClass.getMethod("hi");
hi.invoke(null);
class nte{
static int age=10;
static {
System.out.println("Helloworld");
}
public static void hi(){
System.out.println("hi");
}
}
输出结果
class com.reflection.homework.nte
Helloworld
hi
第一个nte.class 输出后,静态方法块中的打印才输出,说明 使用 类名.class 时类并不会被加载。