java反射机制

    技术2022-07-11  93

    java反射机制

    定义为什么要有反射呢?使用实践

    定义

    Java的反射(reflection)机制是指在程序的运行状态中,可以构造任意一个类的对象,可以了解任意一个对象所属的类,可以了解任意一个类的成员变量和方法,可以调用任意一个对象的属性和方法。这种动态获取程序信息以及动态调用对象的功能称为Java语言的反射机制。

    为什么要有反射呢?

    反射让开发人员可以通过外部类的全路径名创建对象,并使用这些类,实现一些扩展的功能。反射让开发人员可以枚举出类的全部成员,包括构造函数、属性、方法。以帮助开发者写出正确的代码。测试时可以利用反射 API 访问类的私有成员,以保证测试代码覆盖率。 举例子: 1.当我们的程序在运行时,需要动态的加载一些类这些类开始不用加载到jvm,而是在运行时根据需要才加载,举个例子我们的项目底层有时是用mysql,有时用oracle,需要动态地根据实际情况加载驱动类,这个时候反射就有用了,假设 com.java.driver.myqlConnection,com.java.driver.oracleConnection这两个类我们要用,这时候我们的程序就写得比较动态化,通过Class tc = Class.forName(“com.java.dbtest.TestConnection”);通过类的全类名让jvm在服务器中找到并加载这个类, 2.spring,会发现当你配置各种各样的bean时,是以配置文件的形式配置的,配置需要的bean,spring容器就会根据需求去动态加载. 3.在JBDC里也有反射获取加载类,账号,密码

    使用

    反射获取 Class 类 (Class)反射获取类中的所有字段 (Field)反射获取类中的所有构造方法(Constructor)反射获取类中的方法 (Method)

    Field 类:提供有关类的属性信息,以及对它的动态访问权限。它是一个封装反射类的属性的类。 Constructor 类:提供有关类的构造方法的信息,以及对它的动态访问权限。它是一个封装反射类的构造方法的类。 Method 类:提供关于类的方法的信息,包括抽象方法。它是用来封装反射类方法的一个类。 Class 类:正在运行的 Java 应用程序中的类的实例。

    实践

    首先写一个类

    package reflection; /** * 测试类 */ public class TestR { //私有属性name private String name; //公共属性password public String password; //构造方法 public TestR() { } //有参构造方法 public TestR(String name, String password) { this.name = name; this.password = password; } public void setName(String name) { this.name = name; } public String test(String val){ System.out.println(val +" name:"+name+" password:"+password); return "test"; } }

    反射应用

    //通过包路径获取 TestClass Class testClass = Class.forName("com.test.reflection.TestR"); Class testClass1 = TestR.class; //获取字段属性 // 1.获取所有声明的字段属性 Field[] declaredFieldList = testClass.getDeclaredFields(); for (Field declaredField : declaredFieldList) { System.out.println("declared Field: " + declaredField); } // 2.获取所有公有的字段属性 Field[] fieldList = testClass.getFields(); for (Field field : fieldList) { System.out.println(" public field: " + field); } //构造方法 // 3.获取所有声明的构造方法 Constructor[] declaredConstructorList = testClass.getDeclaredConstructors(); for (Constructor declaredConstructor : declaredConstructorList) { System.out.println("testClass declared Constructor: " + declaredConstructor); } // 4.获取所有公有的构造方法 Constructor[] constructorList = testClass.getConstructors(); for (Constructor constructor : constructorList) { System.out.println("testClass constructor: " + constructor); } //方法 // 1.获取所有声明的函数 Method[] declaredMethodList = testClass.getDeclaredMethods(); for (Method declaredMethod : declaredMethodList) { System.out.println("declared Method: " + declaredMethod); } // 2.获取所有公有的函数 Method[] methodList = testClass.getMethods(); for (Method method : methodList) { System.out.println("method: " + method); } Constructor testConstructor = testClass.getDeclaredConstructor(String.class); // 如果私有的函数,需要设置accessible true testConstructor.setAccessible(true); // 使用构造方法的newInstance方法创建对象,传入构造方法所需参数,如果有多个参数,用','连接即可 Object test = testConstructor.newInstance("pengzc","123"); Field testPasswordField = testClass.getDeclaredField("password"); // 使用字段的set方法设置字段值,传入此对象以及参数值 testPasswordField.set(test,"456"); // 4.获取声明的函数,传入所需参数的类名,如果有多个参数,用','连接即可 Method studentShowMethod = testClass.getDeclaredMethod("show",String.class); // 如果私有的函数,需要设置accessible true studentShowMethod.setAccessible(true); // 使用函数的invoke方法调用此函数,传入此对象以及函数所需参数,如果有多个参数,用','连接即可。函数会返回一个Object对象,使用强制类型转换转成实际类型即可 Object result = studentShowMethod.invoke(test,"test哈哈哈哈"); System.out.println("result: " + result);
    Processed: 0.010, SQL: 9