美文网首页
Java反射获取类和对象信息全解析

Java反射获取类和对象信息全解析

作者: 95a6af369245 | 来源:发表于2019-02-19 15:49 被阅读80次

    反射可以解决在编译时无法预知对象和类是属于那个类的,要根据程序运行时的信息才能知道该对象和类的信息的问题。

      在两个人协作开发时,你只要知道对方的类名就可以进行初步的开发了。

      获取类对象

      Class.forName(String clazzName)静态方法

      调用类的class属性,Person.class返回的就是Person的class对象(推荐使用)

      调用某个对象的getClass()方法

      具体使用还是要根据实际来选择,第一种方式是比较自由的,只要知道一个类名就可以了,其不会做该类是否存在的校验,第二种、第三种则会做校验

      获取类的信息

      获取类构造器

      ConnstructorgetConstructor(Class...parameterTypes):返回此Class对象对应类的带指定形参的public构造器

      Constructor[] getConstructors():返回此Class对象对应类的所有public构造器

      Constructor[] getDeclaredConstructor(Class...parameterTypes):返回此class对象对应类的带指定参数的构造器,与构造器的访问权限无关

      Constructor[] getDeclaredConstructors():返回此class对象对应类的所有构造器,与构造器的访问权限无关

      获取类成员方法

      Method getMethod(String name,Class...parameterTypes):返回此class对象对应类的带指定形参的public方法

      Method[] getMethods():返回此class对象所表示的类的所有public方法

      Method getDeclaredMethod(string name,Class...parameterTypes):返回此class对象对应类的带指定形参的方法,与方法访问权限无关

      Method[] getDeclaredMethods():返回此class对象对应类的全部方法,与方法的访问权限无关

      获取类成员变量

      Field getField(String name):返回此class对象对应类的指定名称的public成员变量

      Field[] getFields():返回此class对象对应类的所有public成员变量

      Field getDeclaredField(String name):返回此class对象对应类的指定名称的成员变量,与成员变量访问权限无关

      Field[] getDeclaredFields():返回此class对象对应类的全部成员变量,与成员变量的访问权限无关

      获取类注解

      A getAnnotation(ClassannotationClass):尝试获取该class对象对应类上村子的指定类型的Annotation,如果该类型注解不存在,则返回null

      A getDeclaredAnnotation(ClassannotationClass):这是Java 8中新增的,该方法获取直接修饰该class对象对应类的指定类型的Annotation,如果不存在,则返回null

      Annotation[] getAnnotations():返回修饰该class对象对应类上存在的所有Annotation

      Annotation[] getDeclaredAnnotations():返回修饰该Class对象对应类上存在的所有Annotation

      A[] getAnnotationByType(ClassannotationClass):该方法的功能与前面介绍的getAnnotation()方法基本相似,但由于Java8增加了重复注解功能,因此需要使用该方法获取修饰该类的指定类型的多个Annotation

      A[] getDeclaredAnnotationByType(ClassannotationClass):该方法发功能与前面介绍的getDeclaredAnnotations()方法相似,也是因为Java8的重复注解的功能,需要使用该方法获取直接修饰该类的指定类型的多个Annotation

      获取该类内部类

      Class[] getDeclaredClasses():返回该class队形对应类里包含的全部内部类

      获取该类对象所在的外部类

      Class getDeclaringClass():返回该Class对象对应类所在的外部类

      获取该类对象对应类所实现的接口

      Class[] getInterfaces():返回该Class对象对应类所实现的全部接口

      获取该类对象对应类所继承的父类

      Class getSuperclass():返回该Class对象对应类的超类的Class对象

      获取该类对象对应类的修饰符、所在包、类名等基本信息

      int getModifiers():返回此类或接口的所有修饰符,修饰符由public、protected、private、final、static、abstract等对应的常量组成,返回的整数应使用Modifier工具类的方法来解码,才可以获取真是的修饰符

      Package getPackage():获取该类的包

      String getName():以字符串形式返回此CLass对象所表示的类的简称

      判断该类是否为接口、枚举、注解类型

      boolean isAnnotation():返回此class对象是否表示一个注解类型

      boolean isAnnotationPresent(ClassannotationClass):判断此Class对象是否使用类Annotation修饰

      boolean isAnonymousClass():返回此class对象是否是一个匿名类

      boolean isArray():返回此class对象是否表示一个数组类

      boolean isEnum():返回此class对象是否表示一个枚举

      boolean isInterface():返回此class对象是否表示一个接口

      boolean isInstance(Object obj):判断obj是否是此class对象的实例,该方法可以完全代替instanceof操作符

      public interface Colorable { public void value();

      }

      public class ClassInfo { public static void main(String[] args) throws NoSuchMethodException, SecurityException { Classcls=Colorable.class; System.out.println(cls.getMethod(value)); System.out.println(cls.isAnnotation()); System.out.println(cls.isInterface());

      }

      }

      结果

      public abstract void com.em.Colorable.value()falsetrue

      Java8中新增的方法参数反射

      int getParameterCount():获取该构造器或方法的形参个数

      Parameter[] getParameters():获取该构造器或方法的所有形参

      getModifiers():获取修饰该形参的修饰符

      String getName():获取形参名

      Type getParameterizedType():获取带泛型的形参类型

      ClassgetType():获取形参类型

      boolean isNamePresent():该方法返回该类的class文件中是否包含了方法的形参名信息

      boolean isVarArgs():该方法用于判断该参数是否为个数可变的形参

      public class Test { public void getInfo(String str,Listlist){

      System.out.println(成功);

      }

      }

      public class ClassInfo { public static void main(String[] args) throws NoSuchMethodException, SecurityException {

      Classcls=Test.class;

      Method med=cls.getMethod(getInfo, String.class,List.class);

      System.out.println(med.getParameterCount());

      Parameter[] params=med.getParameters();

      System.out.println(params.length); for(Parameter par:params){

      System.out.println(par.getName());

      System.out.println(par.getType());

      System.out.println(par.getParameterizedType());

      }

      }

      }

      结果

      2

      2arg0class java.lang.Stringclass java.lang.Stringarg1interface java.util.Listjava.util.List

      反射生成对象

      使用Class对象的newInstance()方法创建Class对象的实例,该方法要求要有默认构造器(比较常用)

      先使用Class对象获取指定的Constructor对象,在调用Constructor对象的newInstance()方法来创建该Class对象对应类的实例

      反射调用方法

      Object invoke(Object obj,Object...args):该方法中的obj是执行该方法的主调,后面的args是执行该方法时传入该方法的实参

      public class Test { public Test(String str) {

      System.out.println(str);

      } public void getInfo(String str){

      System.out.println(str);

      }

      }

      public class ClassInfo { public static void main(String[] args) throws Exception { Classcls=Test.class; Constructorconstruct=cls.getConstructor(String.class); Test test=construct.newInstance(初始化); Method med=cls.getMethod(getInfo, String.class);

      med.invoke(test, 调用方法成功);

      }

      }

      结果

      初始化

      调用方法成功

      接下来看官仔细看下面的栗子

      public class Test { public Test(String str) {

      System.out.println(str);

      } //私有方法

      private void getInfo(String str){

      System.out.println(str);

      }

      }

      public class ClassInfo { public static void main(String[] args) throws Exception { Classcls=Test.class; Constructorconstruct=cls.getConstructor(String.class); Test test=construct.newInstance(初始化); //为啥使用这个方法呢?

      Method med=cls.getDeclaredMethod(getInfo, String.class); //为啥使用这个方法呢?

      med.setAccessible(true);

      med.invoke(test, 调用方法成功);

      }

      }

      结果

      初始化

      调用方法成功

      setAccessible(boolean flag):将值设为true,指示该Method在使用是应该取消Java语言的访问权限检查

      访问成员变量值

      getXxx(Object obj):获取obj对象的该成员变量的值。此处的Xxx对应8种基本类型,如果该成员变量的类型是引用类型的,则去掉Xxx部分

      setXxx(Object obj,Xxx val):将obj对象的该成员变量设置为val值。此处的Xxx对应8中基本类型,如果该成员变量的类型是引用类型,则取消set后面的Xxx

      以上两个方法可以方法所有的成员变量,包括private的私有成员变量

      public class Test { private int num; public Test(String str) {

      System.out.println(str);

      } private void getInfo(String str){

      System.out.println(str);

      } public int getNum() { return num;

      } public void setNum(int num) { this.num = num;

      }

      }

      public class ClassInfo { public static void main(String[] args) throws Exception { Classcls=Test.class; Constructorconstruct=cls.getConstructor(String.class); Test test=construct.newInstance(初始化); Method med=cls.getDeclaredMethod(getInfo, String.class);

      med.setAccessible(true);

      med.invoke(test, 调用方法成功); Field fld=cls.getDeclaredField(num);

      fld.setAccessible(true);

      fld.setInt(test, 12); System.out.println(fld.getInt(test));

      }

      }

      结果

      初始化

      调用方法成功

      12

      操作数组

      java.lang.reflect包下有一个Array类,其可以动态创建数组

      static Object newInstance(ClasscomponentType,int...length):创建一个具有指定的元素类型、指定维度的新数组

      static xxx getXxx(Object array,int index):返回array数组中第index个元素。其中xxx是各种基本数据类型,如果数组元素是引用类型,则该方法变为get()

      static void setXxx(Object array,int index,xxx val):将array数组中低index 个元素的值设为val,其中xxx是各种基本数据类型,如果数组元素是引用类型,则该方法变为set()

      public class ArrayInfo {

      public static void main(String[] args) { Object arrays=Array.newInstance(String.class, 3); Array.set(arrays, 0, 第一个); Array.set(arrays, 1, 第二个); Array.set(arrays, 2, 第三个);

      System.out.println(Array.get(arrays, 2));

      }

      }

    相关文章

      网友评论

          本文标题:Java反射获取类和对象信息全解析

          本文链接:https://www.haomeiwen.com/subject/mzkfyqtx.html