【Java SE】反射

好久之前,学过的反射
对反射有点一知半解,今天详细整理了一下

1. 获取Class的对象的方式

  • Class.forName(“全类名”):将字节码文件加载进内存,返回class对象

    多用于配置文件,将类名定义在配置文件中,读取文件,加载类

  • 类名.class :通过类名的属性class获取

    多用于参数的传递

  • 对象.getclass(): getclass()方法任object类中定义看

    多用于对象的获取字节码的方式

  • 结论:同一个字节码文件(*.class)在一次程序运行过程中,只会被加载一次,不论通过哪一种方式获得的Class对象都是一样的

在这里插入图片描述

2. Class对象的功能

2.1 获取功能

  1. 获取成员变量

    • Field[] getFields() : 获取所有的公有变量
    • Field getField(string name):获取指定名称的公有变量
    • Field[] getDeclaredFields():获取所有的成员变量
    • Field getDeclaredField(string name):获取指定名称的变量
		Class testClass = Test.class; // 获取类对象
		Field field = testClass.getDeclaredField("name"); // 获取变量
		field.setAccessible(true); // 解除私有
		Test test = new Test();
		Object string = field.get(test); // 获取私有的值
		System.out.println("我是原来的:" + string);
		field.set(test, "lr"); // 修改私有的值
		Object string1 = field.get(test);
		System.out.println("我是后来的:" + string1);
  1. 获取构造方法

    扫描二维码关注公众号,回复: 11815496 查看本文章
    • constructor<?>getconstructors()
    • Constructorgetconstructor(类<?>…parameterTypes)
    • Constructor getDeclaredConstructor(类<?>… parameterTypes)
    • constructor<?>getDeclaredconstructors()
		Class testClass = Test.class; // 获取类对象
		Constructor constructor = testClass.getConstructor(String.class); // 获取构造方法
		Object test = constructor.newInstance("张三"); // 实例化赋予初值
		System.out.println(test);
  1. 获取成员方法

    • Method[]getMethods()
    • Method getHethod(string name,类<?>… parameterTypes)
    • Method[l getDeclaredMethods()
    • Method getDeclaredMethod(string name,类<?>… parameterTypes)
		Class testClass = Test.class; // 获取类对象
		Test test = new Test(); 
		Method method = testClass.getMethod("test", int.class); // 放入实例化和参数
		method.invoke(test, 1); // 运行该方法
  1. 获取类名

    • String.getName()
  2. Field:成员变量

    • 设置值
      set()
    • 获取值
      get()
    • 忽略访问权限修饰符
      setAccessible(true)
  3. Constructor:构造方法

    • 创建对象
      • newInstance(Object… initargs)
  4. Method:方法对象

    • 执行方法
      • Object invoke(Object obj, Object… args)
    • 获取方法名
      • String getName:获取方法名

3. 案例

  • 需求:写一个框架,不能改变该类的任何代码的前提下,可以帮我们创建任意类的对象,并且执行其中任意的方法
  • 实现
    1. 配置文件
    2. 反射
  • 步骤
    1. 将需要创建的对象的全类名和需要执行的方法定义在配置文件中
    2. 在程序中加载读取配置文件
    3. 使用反射技术来加载类文件进内存
    4. 创建方法
    5. 执行方法

Reflect.Class

package fanshe;

import java.io.InputStream;
import java.lang.reflect.Method;
import java.util.Properties;

public class Reflect {
    
    
	public static void main(String[] args) throws Exception {
    
    
		// 创建对象
		Properties properties = new Properties();
		// 获取类的加载器,可以找到src下的文件
		ClassLoader classLoader = Reflect.class.getClassLoader();
		// 读入文件
		InputStream stream = classLoader.getResourceAsStream("pro.properties");
		// 传入字节流
		properties.load(stream);

		// 获取配置文件中数据
		String className = properties.getProperty("className");
		String methodName = properties.getProperty("methodName");

		// 加载该类进内存
		Class cls = Class.forName(className);
		// 创建对象、实例化
		Object obj = cls.newInstance();

		Method method = cls.getDeclaredMethod(methodName);
		method.invoke(obj);

	}
}

pro.properties

className=fanshe.Person
methodName=sleep

猜你喜欢

转载自blog.csdn.net/qq_40915439/article/details/108741628