🔥码云GVP开源项目 12k star Uniapp+ElementUI 功能强大 支持多语言、二开方便! 广告
1. 什么是反射? > 1. 主要是指程序可以访问,检测和修改它本身状态或行为的一种能力,并能根据自身行为的状态和结果,调整或修改应用所描述行为的状态和相关的语义。 > 2. 反射是java中一种强大的工具,能够使我们很方便的创建灵活的代码,这些代码可以再运行时装配,无需在组件之间进行源代码链接。但是反射使用不当会成本很高! > 2. 反射机制的作用: > 1. 反编译:.class-->.java > 2. 通过反射机制访问java对象的属性,方法,构造方法等; 3. 在这里先看一下sun为我们提供了那些反射机制中的类: java.lang.reflect.Constructor; java.lang.reflect.Field; java.lang.reflect.Method; java.lang.reflect.Modifier; ## 1. Class 对象 ### 1.1 获取Class对象 > 想要利用反射技术,首先获取Class对象,每个类在java虚拟机中的字节码对象,获取Class对象又四种办法 > 1. 通过类本身来获得对象 Class classname = this .getClass(); > 2. 通过子类的实例获取父类对象 ClassName cn = new ClassName(); UserClass = cn.getClass(); Class SubUserClass = UserClass.getSuperclass(); > 3. 通过类名加.class获取对象 Class ForClass = **.**.ClassName. class ;(类在包中的路径加. class ) > 4. 通过类名的字符串获取Class对象 Class ForName = Class.forName( "**.**.ClassName" ); ### 1.2 遍历属性 ~~~ public static List<String> reflectObject(String cla) throws ClassNotFoundException { Class clas = Class.forName(cla); Field[] objFields = clas.getDeclaredFields(); List<String> fields = new ArrayList<String>(); for(int i=0;i<objFields.length;i++){ String fieldJson = "{title:'"; objFields[i].setAccessible(true); // 设置些属性是可以访问的 String name = objFields[i].getName(); fieldJson += name + "', field:'" + name + "', align: 'center', valign: 'middle', sortable: true}"; fields.add(fieldJson); } return fields; } ~~~ ### 1.3 遍历属性,获取值 ~~~ public static Map<String, Object> getKeyAndValue(Object obj) { Map<String, Object> map = new HashMap<String, Object>(); // 得到类对象 Class userCla = (Class) obj.getClass(); /* 得到类中的所有属性集合 */ Field[] fs = userCla.getDeclaredFields(); for (int i = 0; i < fs.length; i++) { Field f = fs[i]; f.setAccessible(true); // 设置些属性是可以访问的 Object val = new Object(); try { val = f.get(obj); // 传入反射的对象,得到此属性的值 map.put(f.getName(), val);// 设置键值 } catch (IllegalArgumentException e) { e.printStackTrace(); } catch (IllegalAccessException e) { e.printStackTrace(); } System.out.println("单个对象的所有键值==反射==" + map.toString()); return map; } ~~~ ## 2. 反射获取泛型参数 getGenericSuperclass():`获取父类类型<T>` ~~~ public class Person<T> { } import java.lang.reflect.ParameterizedType; import java.lang.reflect.Type; public class Student extends Person<Student> { public static void main(String[] args) { Student st=new Student(); Class clazz=st.getClass(); //getSuperclass()获得该类的父类 System.out.println(clazz.getSuperclass()); //getGenericSuperclass()获得带有泛型的父类 //Type是 Java 编程语言中所有类型的公共高级接口。它们包括原始类型、参数化类型、数组类型、类型变量和基本类型。 Type type=clazz.getGenericSuperclass(); System.out.println(type); ParameterizedType p=(ParameterizedType)type; //转成泛型类型 Class c=(Class) p.getActualTypeArguments()[0]; //getActualTypeArguments获取参数化类型的数组,泛型可能有多个 System.out.println(c); } } ~~~ 打印结果: ~~~ class com.test.Person com.test.Person<com.test.Student> class com.test.Student ~~~