Java之反射


Java反射:框架设计的灵魂

设计框架用的,学会能对框架有更好的理解

  • 反射:将类的各个组成部分封装为其他对象,这就是反射机制
    • 好处:
      1. 可以在程序运行过程中,操作这些对象
      2. 可以解耦,提高程序的可拓展性

类对象

什么是类对象

类对象,就是用于描述这种类,都有什么属性,什么方法的

作用:
从class文件里提取出一个类的成员变量构造方法成员方法(主要)
并将其封装成数组Field[] fieldsConstructor[] consMethod[] methods

获取类对象方式

获取类对象有3种方式

  1. Class.forName(“全类名”) //将字节码文件加载进内存,返回Class对象
    • 全类名,就是包名.类名
    • 多用于配置文件,将类名定义在配置文件中。读取文件,加载类
  2. 类名.class //通过类名的属性class获取
    • 多用于参数的传递
  3. 已经实例对象.getClass() //getClass()在Object类中定义着(换句话说:所有类都这个方法)
    • 多用于对象的获取字节码的方式

在一个JVM中,一种类,只会有一个类对象存在。所以以上三种方式取出来的类对象,都是一样的
方法示例:

package reflection;

import charactor.Hero;

public class TestReflection {

    public static void main(String[] args) {
            String className = "charactor.Hero";
            try {
                Class pClass1=Class.forName(className);
                Class pClass2=Hero.class;
                Class pClass3=new Hero().getClass();
                System.out.println(pClass1==pClass2);
                System.out.println(pClass1==pClass3);
            } catch (ClassNotFoundException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
    }
}

获取类对象的时候,会导致类属性被初始化

无论什么途径获取类对象,都会导致静态属性被初始化,而且只会执行一次。(除了直接使用 Class c = Hero.class 这种方式,这种方式不会导致静态属性被初始化)

类对象功能(即获取类的各个部分)

  1. 获取成员变量们

    • Field[] getFields() :获取所有public修饰的成员变量,包括从父类继承来的变量

    • Field getField(String name) :获取指定名称的public修饰的成员变量,包括从父类继承来

    • Field[] getDeclaredFields() :获取所有的成员变量,不考虑修饰符,但是不能获取继承来的字段

    • Field getDeclaredField(String name) :获取指定名称的成员变量,不考虑修饰符,但是不能获取继承来的字段

  2. 获取构造方法们

    • Constructor<?>[] getconstructors()

    • Constructor getconstructor(类… parameterTypes)

    • Constructor getDeclaredconstructor()

    • Constructor<?>[] getDeclaredconstructors()

  3. 获取成员方法们

    • Method[] getMethods()

    • Method getMethod(String name,类)

    • Method[] getDeclaredMethods()

    • Method getDeclaredMethod(String name,类)

  4. 获取类名

    • String getName()

获取类的各个部分之后,进行的操作

  • Field:成员变量

    • 操作

      1. 设置值

        • void set(Object obj,Object value)
      2. 获取值

        • get(Object obj)
      3. 忽略访问权限修饰符的安全检查

        • setAccessible(true) :暴力反射(用于访问和修改private修饰的成员变量的值,对于其他类的部分也能使用)
  • Constructor:构造方法

    • 创建对象:

      • 用获取到的构造器调用newInstance()

      • 如果使用空参数构造方法创建对象,操作可以简化:Class对象的newInstance()方法(Object提供的)

  • Method:方法对象

    • 执行方法

      • Object invoke(Object obj,Object args)
    • 获取方法名称:

      • String getName:获取方法名

文章作者: Sky03
版权声明: 本博客所有文章除特別声明外,均采用 CC BY 4.0 许可协议。转载请注明来源 Sky03 !
评论
 上一篇
Java之注解 Java之注解
注解 概念:说明程序的,给计算机看的 作用分类: 编写文档:通过代码里标识的注解生成文档【生成doc文档】 代码分析:通过代码里标识的注解对代码进行分析【使用注解】 编译检查:通过代码里标识的注解让编译器能够实现基本的编译检查【Overri
2019-02-19
下一篇 
Junit测试 Junit测试
Junit单元测试 测试分类: 黑盒测试:不需要写代码,给输入值,看程序是否能够输出期望的值 白盒测试:需要写代码,关注程序具体的执行流程 Junit使用:白盒测试 步骤: 定义一个测试类(测试用例) 建议命名规则: 测试类名:
2019-02-17
  目录