Java反射基础

java反射是指在运行状态中,对于任意一个类都能够知道这个类所有的属性和方法,
并且可以调用其属性和方法。这种动态获取信息和操作对象方法的功能被称为反射。
简单描述:反射可以实现在运行时获取并操作类的属性和方法。

1 Class类的使用

1.1 获取实例的对象

任何一个类都是Class的实例对象,获取实例的对象有三种方式。

1.1.1 第一种:

任何一个类都有一个隐含的静态成员变量class:

Class class1 = People.class;
1.1.2 第二种:

已经知道该类的对象,通过类对象的getClass方法:

Peaple people = new People();
Class class2 = people.getClass();
1.1.3 第三种:

使用Class的forName方法:

Class class3 = Class.forName("类的全路径");

1.2 通过类的类类型创建该类的对象

通过类的类类型创建该类的对象,前提:有无参构造方法

People people = (People)class3.getInstance();

2 动态加载类

Class.forName("类的全路径")不仅表示类的类类型,还代表了动态加载类。编译时加载类为静态加载类,
运行时加载类为动态加载类。new 创建对象 是静态加载,在编译时刻就需要加载所有可能用到的类。通过
动态加载类就可解决该问题。

3 Class类的基本API

3.1 获取构造函数信息

  • getConstructor(Class…):获取某个public的构造函数;
  • getDeclaredConstructor(Class…):获取某个构造函数;
  • getConstructors():获取所有public的构造函数;
  • getDeclaredConstructors():获取所有构造函数;
public static void getConstructorsMessage(Object obj){
    // 获取类类型,getClass()方法是native修饰的方法
    Class<?> objClass = obj.getClass();
    // 获得所有公有构造方法
    Constructor<?>[] constructors = objClass.getConstructors();
    // 获得自己声明的构造方法
    Constructor<?>[] declaredConstructors = objClass.getDeclaredConstructors();
    for(Constructor<?> constructor : declaredConstructors){
        // 获得参数类型
        Class<?>[] parameterTypes = constructor.getParameterTypes();
        for (Class<?> parameterType : parameterTypes){
            System.out.println("parameterType = " + parameterType);
        }
    }
}

3.2 获取方法信息

3.2.1 通过类的类类型获取方法
  • Method getMethod(name, Class…):获取某个public修饰的方法(包括父类);
  • Method getDeclaredMethod(name, Class…):获取当前类的某个方法(不包括父类);
  • Method[] getMethods():获取所有public修饰的方法(包括父类);
  • Method[] getDeclaredMethods():获取当前类的所有方法(不包括父类);
3.2.2 获取方法信息
  • getName():返回方法名称;
  • getReturnType():返回方法返回值类型,也是一个Class实例;
  • getParameterTypes():返回方法的参数类型,是一个Class数组;
  • getModifiers():返回方法的修饰符。
public class ClassUtil {
    public static void getMethodMessage(Object obj){
        // 获取类类型,getClass()方法是native修饰的方法
        Class<?> objClass = obj.getClass();
        // 获取类的名称
        String className = objClass.getName();
        System.out.println("className = " + className);
        // 获取类所有public方法,包括从父类继承的
        Method[] objClassMethods = objClass.getMethods();
        System.out.println("objClassMethods = " + Arrays.toString(objClassMethods));
        // 获取该类自己声明的所有方法
        Method[] declaredMethods = objClass.getDeclaredMethods();
        for (Method method: declaredMethods) {
            // 获得方法的返回值类型的类类型
            Class<?> returnType = method.getReturnType();
            // 获得方法名称
            String methodName = method.getName();
            System.out.println("methodName = " + methodName + "returnType = " + returnType);
            // 获取参数类型:参数列表的类类型
            Class<?>[] parameterTypes = method.getParameterTypes();
        }
    }
}

3.3 获取属性信息

3.3.1 类的类类型方法获取属性
  • Field getField(name):根据字段名获取某个public的field(包括父类);
  • Field getDeclaredField(name):根据字段名获取当前类的某个field(不包括父类);
  • Field[] getFields():获取所有public的field(包括父类);
  • Field[] getDeclaredFields():获取当前类的所有field(不包括父类);
3.3.2 获取属性信息
  • getName():返回字段名称;
  • getType():返回字段类型,也是一个Class实例;
  • getModifiers():返回字段的修饰符;
public static void getFiledMessage(Object obj) {
        // 获取类类型,getClass()方法是native修饰的方法
        Class<?> objClass = obj.getClass();
        // Filed类封装了关于成员变量的操作
        // 获取该类自己声明的成员变量
        Field[] declaredFields = objClass.getDeclaredFields();
        for(Field field : declaredFields){
            // 获取成员变量的名称
            String name = field.getName();
            // 获取成员变量的类型
            Class<?> type = field.getType();
            System.out.println("name = " + name + "type = " + type);
        }
    }

3.4 继承关系

  • Class getSuperclass():获取父类类型;
  • 使用instanceof操作符判断一个实例是否是某个类型;

4 方法反射的基本操作

public static void invokeMethod(Object obj)
    throws NoSuchMethodException, InvocationTargetException, IllegalAccessException {
    // 获取类类型,getClass()方法是native修饰的方法
    Class<?> objClass = obj.getClass();
    // 根据方法名与参数类型获取方法
    Method start = objClass.getMethod("start", Integer.class, String.class);
    // 执行方法
    Object invoke = start.invoke(obj, 1, "hangzhou");
    System.out.println("invoke = " + invoke);
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

尘风-随手记

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值