Java的反射机制之获取class详解

 更新时间:2023年09月19日 08:43:19   作者:_雨_  
这篇文章主要介绍了Java的反射机制之获取class详解,Class类表示一个类或接口的元数据,通过它可以获取到类或接口的构造函数、方法、字段、注解等信息,也能够创建对象、调用方法等,需要的朋友可以参考下

Class类基本介绍

在Java语言中,每个对象都有一个运行时类,即其所属的类。而这个运行时类在Java中是以Class类的实例形式存在的,该Class类实例就是所谓的Class对象。Class类表示一个类或接口的元数据,通过它可以获取到类或接口的构造函数、方法、字段、注解等信息,也能够创建对象、调用方法等。

1.Class也是类,因此也继承Obiect类

2.Class类对象不是new出来的,而是系统创建的

3.对于某个类的Class类对象,在内存中只有一份,因为类只加载一次

4.每个类的实例都会记得自己是由哪个 Class 实例所生成

5.通过Class对象可以完整地得到一个类的完整结构,通过一系列API

6.Class对象是存放在堆的

7.类的字节码二进制数据,是放在方法区的,有的地方称为类的元数据(包括 方法代码变量名,方法名,访问权限等等)

代码演示:

package com.reflection.class_;
/**
 * 对Class类特点的梳理
 */
public class Class01 {
    public static void main(String[] args) throws ClassNotFoundException {
        //看看Class类图
        //1. Class也是类,因此也继承Object类
        //Class
        //2. Class类对象不是new出来的,而是系统创建的
        //(1) 传统new对象
        /*  ClassLoader类
            public Class<?> loadClass(String name) throws ClassNotFoundException {
                return loadClass(name, false);
            }
         */
        //Cat cat = new Cat();
        //(2) 反射方式, 没有debug到 ClassLoader类的 loadClass, 原因是,我没有注销Cat cat = new Cat();
        /*
            ClassLoader类, 仍然是通过 ClassLoader类加载Cat类的 Class对象
            public Class<?> loadClass(String name) throws ClassNotFoundException {
                return loadClass(name, false);
            }
         */
        Class cls1 = Class.forName("com.Cat");
        //3. 对于某个类的Class类对象,在内存中只有一份,因为类只加载一次
        Class cls2 = Class.forName("com.Cat");
        System.out.println(cls1.hashCode());
        System.out.println(cls2.hashCode());
        Class cls3 = Class.forName("com.Dog");
        System.out.println(cls3.hashCode());
    }
}
  • forName(String className):根据类的全限定名获取对应的类对象。
  • newInstance():创建一个类的对象,要求该类必须具有默认的构造方法。
  • getConstructor(Class<?>… parameterTypes):获取指定参数类型的构造方法。
  • getDeclaredConstructor(Class<?>… parameterTypes):获取该类中声明的指定参数类型的构造方法,即使该构造方法是私有的也可以获取到。
  • getMethod(String name, Class<?>… parameterTypes):获取指定方法名和参数类型的公有方法。
  • getDeclaredMethod(String name, Class<?>… parameterTypes):获取该类中声明的指定方法名称和参数类型的方法,即使该方法是私有的也可以获取到。
  • getField(String name):获取指定名称的公有字段。
  • getDeclaredField(String name):获取该类中声明的指定名称的字段,即使该字段是私有的也可以获取到。

代码演示:

package com.reflection.class_;
import com.Car;
import java.lang.reflect.Field;
/**
 * 演示Class类的常用方法
 */
public class Class02 {
    public static void main(String[] args) throws ClassNotFoundException, IllegalAccessException, InstantiationException, NoSuchFieldException {
        String classAllPath = "com.Car";
        //1 . 获取到Car类 对应的 Class对象
        //<?> 表示不确定的Java类型
        Class<?> cls = Class.forName(classAllPath);
        //2. 输出cls
        System.out.println(cls); //显示cls对象, 是哪个类的Class对象 com.Car
        System.out.println(cls.getClass());//输出cls运行类型 java.lang.Class
        //3. 得到包名
        System.out.println(cls.getPackage().getName());//包名
        //4. 得到全类名
        System.out.println(cls.getName());
        //5. 通过cls创建对象实例
        Car car = (Car) cls.newInstance();
        System.out.println(car);//car.toString()
        //6. 通过反射获取属性 brand
        Field brand = cls.getField("brand");
        System.out.println(brand.get(car));//宝马
        //7. 通过反射给属性赋值
        brand.set(car, "奔驰");
        System.out.println(brand.get(car));//奔驰
        //8 我希望大家可以得到所有的属性(字段)
        System.out.println("=======所有的字段属性====");
        Field[] fields = cls.getFields();
        for (Field f : fields) {
            System.out.println(f.getName());//名称
        }
    }
}
 

如何获取class类对象

1.前提: 已知一个类的全类名,且该类在类路径下,可通过Class类的静态方法forName0获取,可能抛出ClassNotFoundException,实例: Class cls1Class.forName("iava.lana.Cat”):

应用场景:多用于配置文件,读取类全路径,加载类

2.前提:若已知具体的类,通过类的class 获取,该方式 最为安全可靠,程序性能最高实例: Class cls2 = Catclass;

应用场景:多用于参数传递,比如通过反射得到对应构造器对象

3.前提: 已知某个类的实例,调用该实例的getClass(方法获取Class对象,实例Class clazz = 对象getClass0://运行类型

应用场景: 通过创建好的对象,获取Class对象

4.其他方式ClassLoader cl = 对象.getClass().getClassLoader();

Class clazz4=cl.loadClass("类的全类目");

5.基本数据(int, char,boolean,float,double,byte,long,short) 按如下方式得到Class类对象

6.基本数据类型对应的包装类,可以通过 .type 得到Class类对象

代码演示:

package com.reflection.class_;
import com.Car;
/**
 * 演示得到Class对象的各种方式(6)
 */
public class GetClass_ {
    public static void main(String[] args) throws ClassNotFoundException {
        //1. Class.forName
        String classAllPath = "com.Car"; //通过读取配置文件获取
        Class<?> cls1 = Class.forName(classAllPath);
        System.out.println(cls1);
        //2. 类名.class , 应用场景: 用于参数传递
        Class cls2 = Car.class;
        System.out.println(cls2);
        //3. 对象.getClass(), 应用场景,有对象实例
        Car car = new Car();
        Class cls3 = car.getClass();
        System.out.println(cls3);
        //4. 通过类加载器【4种】来获取到类的Class对象
        //(1)先得到类加载器 car
        ClassLoader classLoader = car.getClass().getClassLoader();
        //(2)通过类加载器得到Class对象
        Class cls4 = classLoader.loadClass(classAllPath);
        System.out.println(cls4);
        //cls1 , cls2 , cls3 , cls4 其实是同一个对象
        System.out.println(cls1.hashCode());
        System.out.println(cls2.hashCode());
        System.out.println(cls3.hashCode());
        System.out.println(cls4.hashCode());
        //5. 基本数据(int, char,boolean,float,double,byte,long,short) 按如下方式得到Class类对象
        Class<Integer> integerClass = int.class;
        Class<Character> characterClass = char.class;
        Class<Boolean> booleanClass = boolean.class;
        System.out.println(integerClass);//int
        //6. 基本数据类型对应的包装类,可以通过 .TYPE 得到Class类对象
        Class<Integer> type1 = Integer.TYPE;
        Class<Character> type2 = Character.TYPE; //其它包装类BOOLEAN, DOUBLE, LONG,BYTE等待
        System.out.println(type1);
        System.out.println(integerClass.hashCode());//?
        System.out.println(type1.hashCode());//?
    }
}

哪些类型有Class对象

1.外部类,成员内部类,静态内部类,局部内部类,匿名内部类

2interface : 接口

3.数组

4.enum:枚举

5.annotation:注解

6.基本数据类型

7.void

代码演示:

package com.reflection.class_;
import java.io.Serializable;
/**
 * 演示哪些类型有Class对象
 */
public class AllTypeClass {
    public static void main(String[] args) {
        Class<String> cls1 = String.class;//外部类
        Class<Serializable> cls2 = Serializable.class;//接口
        Class<Integer[]> cls3 = Integer[].class;//数组
        Class<float[][]> cls4 = float[][].class;//二维数组
        Class<Deprecated> cls5 = Deprecated.class;//注解
        //枚举
        Class<Thread.State> cls6 = Thread.State.class;
        Class<Long> cls7 = long.class;//基本数据类型
        Class<Void> cls8 = void.class;//void数据类型
        Class<Class> cls9 = Class.class;//
        System.out.println(cls1);
        System.out.println(cls2);
        System.out.println(cls3);
        System.out.println(cls4);
        System.out.println(cls5);
        System.out.println(cls6);
        System.out.println(cls7);
        System.out.println(cls8);
        System.out.println(cls9);
    }
}

到此这篇关于Java的反射机制之获取class详解的文章就介绍到这了,更多相关Java的反射机制内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • SpringBoot访问外部文件及默认路由问题

    SpringBoot访问外部文件及默认路由问题

    这篇文章主要介绍了SpringBoot访问外部文件及默认路由问题,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教
    2022-11-11
  • Javassist之一秒理解java动态编程

    Javassist之一秒理解java动态编程

    概述Javassist是一款字节码编辑工具,可以直接编辑和生成Java生成的字节码,以达到对.class文件进行动态修改的效果。
    2019-06-06
  • Java 实战练习之网上电商项目的实现

    Java 实战练习之网上电商项目的实现

    读万卷书不如行万里路,只学书上的理论是远远不够的,只有在实战中才能获得能力的提升,本篇文章手把手带你用java+vue+Springboot+ssm+mysql+maven+redis实现一个网上电商项目,大家可以在过程中查缺补漏,提升水平
    2021-11-11
  • Java文件IO操作教程之DirectIO的意义

    Java文件IO操作教程之DirectIO的意义

    这篇文章主要给大家介绍了关于Java文件IO操作教程之DirectIO的相关资料,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面来一起学习学习吧
    2019-03-03
  • Java中减少if-else的设计模式和优化技巧

    Java中减少if-else的设计模式和优化技巧

    “过于依赖 if-else 不仅会让代码变得臃肿不堪,还会使维护成本大大增加,其实,if-else 虽然是最基础的条件分支,但它并不是万能的解决方案,今天,我将带大家了解一些取代 if-else 的设计模式和优化技巧,需要的朋友可以参考下
    2025-04-04
  • SpringBoot整合MongoDB的示例

    SpringBoot整合MongoDB的示例

    这篇文章主要介绍了SpringBoot整合MongoDB的示例,帮助大家更好的理解和学习springboot框架,感兴趣的朋友可以了解下
    2020-10-10
  • Java毕业设计实战项目之仓库管理系统的实现流程

    Java毕业设计实战项目之仓库管理系统的实现流程

    这是一个使用了java+SSM+Maven+Bootstrap+mysql开发的仓库管理系统,是一个毕业设计的实战练习,具有一个仓库管理系统该有的所有功能,感兴趣的朋友快来看看吧
    2022-01-01
  • junit4教程junit4.5官方下载

    junit4教程junit4.5官方下载

    前提:本文假设读者已经具有使用JUnit 4以前版本的经验。
    2008-09-09
  • javax.mail.SendFailedException: Sending failed问题原因

    javax.mail.SendFailedException: Sending failed问题原因

    这篇文章主要介绍了javax.mail.SendFailedException: Sending failed问题原因,需要的朋友可以参考下
    2015-05-05
  • Java对称加密算法DES实例详解

    Java对称加密算法DES实例详解

    这篇文章主要介绍了Java对称加密算法DES,结合实例形式详细分析了java DES算法的概念、原理、实现方法与应用场景,需要的朋友可以参考下
    2019-09-09

最新评论