反射机制是什么
反射机制是在运行状态中,对于任意一个类,都能够知道这个类的所有属性和方法;对于任意一个对象,都能够调用它的任意一个方法和属性;这种动态获取的信息以及动态调用对象的方法的功能称为java语言的反射机制。
反射机制能做什么
在框架中很常用,不需要写死代码
反射机制的相关API
获取Class对象
Class clazz1 = Class.forName("com.gold.m_demo.Employee");Class clazz2 = new Employee().getClass();Class clazz3 = Employee.class;
获取对象的父类及接口
Class clazz = Class.forName("com.gold.m_demo.Employee");Class parentClass =clazz.getSuperclass();Class [] interfaces = clazz.getInterfaces();
获取类的构造方法
Class clazz = Class.forName("com.gold.m_demo.Employee");//获取所有public的构造函数Constructor [] constructors = clazz.getConstructors();//根据参数类型获取指定public的构造函数Constructor constructor2 = clazz.getConstructor(String.class,Integer.class);//获取所有的构造函数Constructor [] constructors3 =clazz.getDeclaredConstructors();//根据参数类型获取指定构造函数Constructor constructor4 = clazz.getDeclaredConstructor(String.class);
动态创建对象
Class clazz = Class.forName("com.gold.m_demo.Employee");//方式一:必须提供无参构造函数Employee employee1 = (Employee)clazz.newInstance();//方式二:根据参数来创建指定数据库Constructor constructor2 = clazz.getConstructor(String.class,Integer.class);Employee employee2 = (Employee)constructor2.newInstance("jack",18);
获取类的属性
//根据变量名,返回一个具体的具有public属性的成员变量Field field = clazz.getField("createTime"); //返回具有public属性的成员变量的数组Field[] fields = clazz.getFields(); //返回所有成员变量组成的数组(不分public和非public属性) Field[] fields2 = clazz.getDeclaredFields();
Field的其他信息
Field[] fields = clazz.getDeclaredFields(); for (Field field : fields) { //获取权限修饰符 int mo = field.getModifiers(); System.out.print(Modifier.toString(mo)); //获取属性类型 System.out.print("\t"+field.getType()); //获取属性名 System.out.print("\t"+field.getName()); System.out.println(); }
获取类的方法
Class clazz = Class.forName("com.gold.m_demo.Employee"); //根据方法名和参数,返回一个具体的具有public属性的方法 Method method = clazz.getMethod("setName", String.class); //返回所有(包括父类)具有public属性的方法数组 Method[] methods=clazz.getMethods(); //返回该类中的所有的方法数组(不分public和非public属性) Method[] methods2=clazz.getDeclaredMethods();
Method的其他方法
Method[] methods=clazz.getMethods(); for (Method m : methods) { if(m.getName().equals("wait")){ System.out.println(m); Class [] parasTypes = m.getParameterTypes(); Class returnType = m.getReturnType(); Class [] exceptionTypes = m.getExceptionTypes(); } }
调用类的方法
Class clazz = Class.forName("com.gold.m_demo.Employee"); //获取方法,然后在调用方法 Method method = clazz.getMethod("setName", String.class); method.invoke(clazz.newInstance(),"rose"); Method method2 = clazz.getMethod("hello", String.class,Integer.class); method2.invoke(clazz.newInstance(), "jack",18);
操作类的属性
Class clazz = Class.forName("com.gold.m_demo.Employee"); Object obj =clazz.newInstance(); //获取属性,赋值 Field field = clazz.getDeclaredField("name"); field.setAccessible(true); field.set(obj, "杰克"); //取值 System.out.println(field.get(obj));
反射机制的应用实例
在泛型Integer的ArrayList中存放一个String类型的对象
ArrayListlist=new ArrayList<>(); Method method=list.getClass().getMethod("add", Object.class);method.invoke(list, "abc"); System.out.println(list.get(0));
通过反射取得并修改数组的信息
int[] intArr = { 1, 2, 3, 4, 5 }; Class clazz = intArr.getClass().getComponentType(); System.out.println("数组类型:" + clazz.getName()); System.out.println("数组长度:" + Array.getLength(intArr)); System.out.println("数组第一个元素:" + Array.getInt(intArr, 0)); Array.set(intArr, 0, 100); System.out.println("修改后第一个元素:" + Array.getInt(intArr, 0));
通过反射修改数组的大小
int[] intArr = { 1, 2, 3, 4, 5 }; Class componetType=intArr.getClass().getComponentType();Object obj = Array.newInstance(componetType, 10); System.arraycopy(intArr, 0, obj, 0, intArr.length); int[] newIntArr =(int[])obj; System.out.println(Arrays.toString(newIntArr));