Java 反射基础

概述

Java反射(Reflection)是Java编程语言的一个特性,它允许在运行时对类、接口、字段和方法进行动态查询和操作。反射提供了一种在运行时查看和修改程序行为的能力,这通常用于实现一些高级功能,如框架、ORM(对象关系映射)工具、IDE(集成开发环境)等。 

1. 反射基础

1.1. 反射的用途 

Java反射角度简单理解spring IOC容器-CSDN博客

1.2.获取class对象的三种方式

反射是基于class对象来操作的,获取class对象的三种方式如下:

  • Class.forName("全类名") --> 对应类在源码阶段
    /** 该方法最常使用
     * 由于编译时无法确定(运行时才能确认)该class object是一个什么类的对象,故而用?代替
     * 使用该方法,会立即触发类的初始化,类的静态初始化块会被执行。
     * 也就是静态代码块在new 实例化对象之前就已经加载了
     */
     Class<?> clazz = Class.forName("com.mycompany.myreflect.Student");
            System.out.println(clazz);
  • 类名.class --> 对应类在加载阶段
    /*       第二种方法一般是当做参数进行传递
    *      如: synchronized(Student.class)
    */
    Class<Student> clazz = Student.class;
    System.out.println(clazz);
  • 对象.getClass --> 对应类在运行阶段
    /*这种方法 当我们已经有这个类的对象时,才可以使用*/
    Student s = new Student();
            Class<? extends Student> clazz = s.getClass();
            System.out.println(clazz);

更多理解可参考:Java 类加载和实例化对象的过程-CSDN博客 

1.3. 反射的基本API

Java反射API主要位于java.lang.reflect包中,包括以下几个核心类:

  • Class:表示类、接口、数组类、基本数据类型、以及void的Class对象。
  • Field:表示类的成员变量(包括实例变量和类变量)。
            Field[] fieldsType1 = clazz.getFields();
            //getFields 可以获得自己及父类(可以递归获得父类的父类的)的公共字段,不可以获得自己的或父类的私有字段
            for (Field field : fieldsType1){
                System.out.println(field);
            }
    
            System.out.println("------------------------------");
            // getDeclaredFields 可以获取自己的所有字段(私有和共有),但是不能获得父类的任何字段
            Field[] fieldsType2 = clazz.getDeclaredFields();
            for (Field field : fieldsType2){
                System.out.println(field);
            }
    
            System.out.println("------------------------------");
            // 获取父类的所有构造方法
            Field[] fieldsParentsAll = clazz.getSuperclass().getDeclaredFields();
            for (Field field : fieldsParentsAll){
                System.out.println(field);
            }
  • Method:表示类的方法。
            Method[] methods = clazz.getMethods();
            Method[] methods1 = clazz.getDeclaredMethods();
            Method method = clazz.getMethod("getName");
    //获取特定方法,括号内是方法名,入参类型
            Method method1 = clazz.getMethod("functionA",String.class);
    //获取方法的修饰符对应的值
    System.out.println("method modifiers:"+method.getModifiers());
    //执行静态方法
    method.invoke(null);
    //执行非静态方法
    method1.invoke(student);
  • Constructor:表示类的构造方法。
    // 返回所有公共构造方法对象的数组     
        Constructor<?>[] constructors1  = clazz.getConstructors();
    
    // 返回所有构造方法对象的数组     
        Constructor<?>[] constructors2 = clazz.getDeclaredConstructors();
    
    // 返回单个特定公共构造方法对象,括号内的是该构造方法的参数类型
        Constructor<Student> constructor3 = (Constructor<Student>);
    
    // 返回单个特定构造方法对象,括号内的是该构造方法的参数类型
        Constructor<Student> constructor4 = (Constructor<Student>); 
  • Annotation: 获取注解
         Annotation[] annotations = clazz.getAnnotations();
         Annotation[] annotations2 = clazz.getDeclaredAnnotations();
         Annotation annotation = clazz.getDeclaredAnnotation(MyAnnotation.class);
         Annotation annotation2 = clazz.getAnnotation(MyAnnotation.class);
     
  • 26
    点赞
  • 30
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值