目录
反射的基本概念
反射的定义:在程序运行过程中分析类的一种能力。
正常情况:
反射:
反射的作用
(1)分析类。加载并初始化一个类,查看类的所有属性和方法。
(2)查看并使用对象。查看一个对象的所有属性和方法,使用对象的任意属性和方法。
反射的应用场景
1、构建通用的工具
2、搭建具有高度灵活性和扩展性的系统框架
3、逆向工程中常用反射
获取字节码的三种方式
举例:在如图
/*
* 获取class对象的三种方式
* */
public class ReflectDemo1 {
public static void main(String[] args) throws ClassNotFoundException {
// 方式一
Student stu = new Student();
Class clazz1 = stu.getClass();
// 方式二
Class clazz2 = Student.class;
// 方式三
Class clazz3 = Class.forName("itcast.Student");
System.out.println(clazz1.equals(clazz2));
System.out.println(clazz2.equals(clazz3));
}
}
下面三个反射例子要用到的Student类
public class Student {
public String name;
private int age;
public Student(){
}
public Student(String name){
System.out.println("录入的名字是: " + name);
}
private Student(int age){
System.out.println("录入的年龄是: " + age);
}
public void show1(){
System.out.println("公共的空参方法");
}
public void show2(int a){
System.out.println("公共的带参方法");
}
private int show3(int a,int b){
System.out.println("私有的带参方法");
return a+b;
}
@Override
public String toString() {
return "Student{" +
"name='" + name + '\'' +
", age=" + age +
'}';
}
}
反射获取构造方法
constructor
import java.lang.reflect.Constructor;
/*
* 通过反射的方式创建:Student类型的对象
* */
public class ReflectDemo2 {
public static void main(String[] args) throws Exception {
// 第1步:获取Student类的字节码文件对象
Class clazz = Class.forName("itcast.Student");
// 第2步:获取指定的构造器对象
// 2.1获取公共的无参构造
Constructor con1 = clazz.getConstructor();
// 2.2获取公共的有参数构造
Constructor con2 = clazz.getConstructor(String.class);
// 2.3获取私有的有参数构造
Constructor con3 = clazz.getDeclaredConstructor(int.class);
// 2.4获取所有公共的构造函数
Constructor[] cons = clazz.getConstructors();
//查看构造器属于哪个类
//String name = con2.getName();
//System.out.println(name);
// 第3步:根据构造器对象和参数,创建对应的Student对象
Student stu = (Student)con2.newInstance("张三");
System.out.println(stu);
// 第4步:打印结果
System.out.println("***********");
System.out.println(con1);
System.out.println(con2);
System.out.println(con3);
System.out.println("*******************");
for(Constructor con:cons){
System.out.println(con);
}
}
}
反射获取成员方法
Method
import java.lang.reflect.Constructor;
import java.lang.reflect.Method;
/*
* 通过反射的方式获取Student类中的成员方法
* */
public class ReflectDemo3 {
public static void main(String[] args) throws Exception{
Class clazz = Class.forName("itcast.Student");
//获取该类的构造器对象,然后创建Student类的对象
Constructor con = clazz.getConstructor();
Student stu = (Student)con.newInstance();
//获取成员方法和调用
Method me1 = clazz.getMethod("show1");
me1.invoke(stu);
Method me2 = clazz.getMethod("show2",int.class); //int.class
me2.invoke(stu,1);
Method me3 = clazz.getDeclaredMethod("show3", int.class, int.class);
me3.setAccessible(true); //私有的方法需要再获取一下权限,开启暴力反射
int sum = (int)me3.invoke(stu,1,2);
System.out.println(sum);
//获取Student类中的所有成员方法
Method[] methods = clazz.getMethods();
for (Method method : methods) {
System.out.println(method);
}
}
}
反射获取成员变量
Field
import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
/*
* 通过反射的方式获取Student类中的属性
* */
public class ReflectDemo4 {
public static void main(String[] args) throws Exception{
Class clazz = Class.forName("itcast.Student");
Constructor con = clazz.getConstructor();
Student stu = (Student)con.newInstance();
Field field1 = clazz.getField("name");
field1.set(stu,"zhang san");
Field field2 = clazz.getDeclaredField("age");
field2.setAccessible(true);
field2.set(stu,15);
System.out.println(stu);
}
}