当前位置: 首页> 游戏> 评测 > 东莞网站推广推广软件_工信部网站备案查询步骤_百度用户服务中心客服电话_google网页搜索

东莞网站推广推广软件_工信部网站备案查询步骤_百度用户服务中心客服电话_google网页搜索

时间:2025/7/14 0:36:05来源:https://blog.csdn.net/azyouyouyou/article/details/144905567 浏览次数:0次
东莞网站推广推广软件_工信部网站备案查询步骤_百度用户服务中心客服电话_google网页搜索

Class类

Class类是Java反射机制的核心类之一。它代表了一个类的元数据,并提供了访问该类信息的功能。通过Class类,可以在运行时动态地获取类的名称、字段、方法、构造方案、父类等信息。更重要的是,class类能够在你在程序运行的时候创建对象。

通俗来讲,Class类就是   我们编写的class 也就是类的模版,它定义了 一个类需要的信息和它的结构,由Class 我们可以知道,类的结构是怎么样的。

当虚拟机在进行了类加载的时候,会先找到类路径下的.class文件,然后根据内容创建Class对象,根据Class对象内部的信息,我们可以创建一个具体的类对象。

也可以把Class类理解成 对类的抽象,它定义了  类应该由什么组成 比如说:类名、构造方法、属性、行为、父类、接口等信息。

 这里需要意一下,Class类是一个泛型类,同时每一个对象只能有一个Class,类模版与类一对一。

Field类

Field 类是 Java 反射机制的一部分。它代表类的一个成员变量(字段),并提供对这些字段的访问能力。通过 Field 类,你可以在运行时获取关于类字段的信息,并且可以通过反射机制动态地访问或修改这些字段的值。

Field 类的主要功能包括:

  • 获取字段的名称、类型、修饰符等信息
  • 通过反射访问字段的值(包括私有字段);
  • 修改字段的值

通俗的理解,可以把Field 作为 类属性的抽象,可以获取属性相关的一些信息。Class类模版包含Field。

Method类

它代表 Java 类中的一个方法,并允许在运行时动态地访问、调用方法。

Method 类主要用于获取有关类方法的信息,并通过反射调用这些方法。它支持访问方法的参数、返回类型、修饰符等信息,并提供调用方法的能力。

Class类模版包含Method。

反射基本使用方法

获取Class对象的三个方法,JDK提供了三种获取类模版的方法和其他方法,下面我们逐个学习一下。

public class RefectTest {public static void main(String[] args) throws ClassNotFoundException {// 类型.class 获取Class<RefectTest> refectTestClass = RefectTest.class;System.out.println(refectTestClass.getName());  // 获取类名System.out.println(refectTestClass.getSimpleName()); // 获取简单类名System.out.println(refectTestClass.getCanonicalName()); // 获取标准类名System.out.println("---------------------------------------------------------------------");// 对象.getClass() 获取RefectTest refectTest = new RefectTest();Class<? extends RefectTest> refectTestClass1 = refectTest.getClass();System.out.println(refectTestClass1.getName());System.out.println("---------------------------------------------------------------------");// Class.forName(类全限定名) 获取Class<?> refectTestClass2 = Class.forName("com.shifei.test.springredis.RefectTest");System.out.println(refectTestClass2.getName());}
}

获取类的名称

System.out.println(refectTestClass.getName());   // 类名称System.out.println(refectTestClass.getSimpleName());  // 简单类名称 只有类名 没有包路径System.out.println(refectTestClass.getCanonicalName()); // 标准的类名称

获取类的父类

        Class<? super RefectTest> superclass = refectTestClass.getSuperclass();System.out.println(superclass.getName());

获取类的接口

        Class<?>[] interfaces = refectTestClass.getInterfaces();for (Class<?> anInterface : interfaces){System.out.println(anInterface.getName());}

获取类的属性

        // 只获取公开的  访问修饰符 是public的Field[] fields = refectTestClass.getFields();for (Field field : fields){System.out.println(field.getName());}System.out.println("---------------------------------------------------------------------");Field[] fields1 = refectTestClass.getDeclaredFields();// 获取全部访问修饰符for (Field field : fields1){System.out.println(field.getName());}

修改类的属性

        RefectTest refectTest = new RefectTest();try {// 根据名称获取 忽略访问权限修饰Field privateFiled = refectTestClass.getDeclaredField("privateFiled");// 对私有的访问 需要修改访问权限 打破封装(对私有操作必须有)privateFiled.setAccessible(true);// 给创建出来的对象的私有属性设置值privateFiled.set(refectTest,"123");System.out.println(privateFiled.get(refectTest));} catch (NoSuchFieldException e) {e.printStackTrace();} catch (IllegalAccessException e) {e.printStackTrace();}

获取 构造器方法

        try {// 获取无参构造方法 Declared  忽略访问权限Constructor<RefectTest> declaredConstructor = refectTestClass.getDeclaredConstructor();// 根据构造方法类型获取构造器Constructor<RefectTest> declaredConstructor1 = refectTestClass.getDeclaredConstructor(String.class, String.class);//  有什么用  构造器有啥用 创建对象被RefectTest refectTest = declaredConstructor.newInstance();System.out.println(refectTest);RefectTest refectTest1 = declaredConstructor1.newInstance("123", "456");System.out.println(refectTest1);} catch (NoSuchMethodException e) {e.printStackTrace();} catch (InvocationTargetException e) {throw new RuntimeException(e);} catch (InstantiationException e) {e.printStackTrace();} catch (IllegalAccessException e) {e.printStackTrace();}RefectTest{privateFiled='null', publicFiled='null'}RefectTest{privateFiled='123', publicFiled='456'}

获取全部方法

        Method[] declaredMethods = refectTestClass.getDeclaredMethods();for (Method method : declaredMethods){System.out.println(method.getName());}

执行方法

        RefectTest refectTest = new RefectTest();Method method = null;try {method = refectTestClass.getMethod("setPublicFiled", String.class);method.invoke(refectTest,"123");System.out.println(refectTest.getPublicFiled());} catch (NoSuchMethodException e) {e.printStackTrace();}catch (IllegalAccessException e) {e.printStackTrace();} catch (InvocationTargetException e) {e.printStackTrace();}

场景实践

反射获取方法时会面临一个问题,就是多态,你传入的参数类型,不是方法中入参的类型而是它的子类,那么在获取方法动态用参数的类型去匹配方法就会找不到(坑)

解决思路   先判断参数数量,然后循环判断动态传入的参数类型是否是方法参数类型的子类

 获取全部的方法 

循环匹配方法名

判断每个方法参数数量与方法入参数量是否一致 不一致返回false

如果一致则判断是否是子类型

注意参数传入顺序

 /***   根据 方法名、参数类型 匹配方法* @param clazz  获取全部方法的Class类* @param methodName  需要获取的方法名称* @param inputParamTypes  需要获取方法的参数列表类型(注意顺序)* @return  返回匹配的方法对象*/@Nullablepublic static Method matchMethod(Class<?> clazz,String methodName,Class<?>[] inputParamTypes){Method[] declaredMethods = clazz.getDeclaredMethods();for (Method method : declaredMethods){if (method.getName().equals(methodName) && paramTypeMatch(method.getParameterTypes(),inputParamTypes)){return method;}}return null;}public static boolean paramTypeMatch(Class<?>[] parameterTypes,Class<?>[] inputParamTypes){if (parameterTypes.length != inputParamTypes.length){return false;}for (int i = 0; i < parameterTypes.length; i++){if (!parameterTypes[i].isAssignableFrom(inputParamTypes[i])) {return false;}}return true;}

 未完待续

关键字:东莞网站推广推广软件_工信部网站备案查询步骤_百度用户服务中心客服电话_google网页搜索

版权声明:

本网仅为发布的内容提供存储空间,不对发表、转载的内容提供任何形式的保证。凡本网注明“来源:XXX网络”的作品,均转载自其它媒体,著作权归作者所有,商业转载请联系作者获得授权,非商业转载请注明出处。

我们尊重并感谢每一位作者,均已注明文章来源和作者。如因作品内容、版权或其它问题,请及时与我们联系,联系邮箱:809451989@qq.com,投稿邮箱:809451989@qq.com

责任编辑: