反射机制的深入应用
1 通过反射调用类中的方法
---------------------------调用无参数方法
1 public class InstanceDemo { 2 public static void main(String[] args) { 3 Class<?> c = null; 4 try { 5 c = Class.forName("com.matto.InstanceDemo.Person"); 6 } catch (Exception e) { 7 e.printStackTrace(); 8 } 9 try { 10 Method met = c.getMethod("say"); //指定将调用这个没有参数的方法 11 met.invoke(c.newInstance()); //调用方法,必须传递对象实例 12 } catch (Exception e) { 13 e.printStackTrace(); 14 } 15 16 } 17 }
---------------------------调用有参数方法
1 public class InstanceDemo { 2 public static void main(String[] args) { 3 Class<?> c = null; 4 try { 5 c = Class.forName("com.matto.InstanceDemo.Person"); 6 } catch (Exception e) { 7 e.printStackTrace(); 8 } 9 try { 10 Method met = c.getMethod("sayChina",String.class,int.class); //指定将调用这个有参数的方法 11 String rv = (String)met.invoke(c.newInstance(),"Matto",30); //调用方法,必须传递对象实例,并传入两个参数 12 //此方法的返回值是String类型,故以String接收 13 System.out.println(rv); 14 } catch (Exception e) { 15 e.printStackTrace(); 16 } 17 18 } 19 }
2 调用getter与setter方法
1 public class InstanceDemo { 2 public static void main(String[] args) { 3 Class<?> c = null; 4 Object object = null; 5 try { 6 c = Class.forName("com.matto.InstanceDemo.Person"); 7 } catch (Exception e) { 8 e.printStackTrace(); 9 } 10 try { 11 object = c.newInstance(); 12 } catch (Exception e) { 13 e.printStackTrace(); 14 } 15 setter(object,"name","Matto",String.class); 16 setter(object,"age",28,int.class); 17 System.out.print("姓名:"); 18 getter(object,"name"); 19 System.out.print("年龄:"); 20 getter(object,"age"); 21 } 22 23 //单词首字母大写 24 public static String initStr(String old){ 25 String string = old.substring(0,1).toUpperCase() + old.substring(1); 26 return string; 27 } 28 29 /** 30 * 31 * @param object 操作的对象 32 * @param att 操作的属性 33 * @param value 设置的值 34 * @param type 参数类型,就是要设置的值的类型 35 */ 36 //调用setter方法 37 public static void setter(Object object,String att,String value,Class<?> type){ 38 Method met = null; 39 try { 40 met = object.getClass().getMethod("set" + initStr(att),type); 41 met.invoke(object,value); 42 } catch (Exception e) { 43 e.printStackTrace(); 44 } 45 } 46 47 //调用getter方法 48 public static void getter(Object object,String att){ 49 try { 50 Method met = object.getClass().getMethod("get" + initStr(att)); 51 System.out.println(met.invoke(object,att)); //接收方法的返回值 52 } catch (Exception e) { 53 e.printStackTrace(); 54 } 55 } 56 }
3 通过反射操作属性---此方法不推荐,原因是此方法以扩大类属性的访问权限后直接操作属性。 最好使用上述的 getter和setter方法
1 public class InstanceDemo { 2 public static void main(String[] args) { 3 Class<?> c = null; 4 Object object = null; 5 try { 6 c = Class.forName("com.matto.InstanceDemo.Person"); 7 object = c.newInstance(); 8 //获取属性 9 Field nameField = c.getDeclaredField("name"); 10 Field ageField = c.getDeclaredField("age"); 11 //设置可外部访问,并设置值 12 nameField.setAccessible(true); 13 nameField.set(object,"Matto"); 14 ageField.setAccessible(true); 15 ageField.set(object,28); 16 //通过get取得属性内容 17 System.out.println("name : " + nameField.get(object)); 18 System.out.println("age : " +ageField.get(object)); 19 20 } catch (Exception e) { 21 e.printStackTrace(); 22 } 23 } 24 }
4 通过反射操作数组:反射机制不仅只能用于类上,还可以应用在任意的引用数据类型的数据上。
------------------得到数组信息并修改数组内容
1 public class InstanceDemo { 2 public static void main(String[] args) { 3 int temp[] = {1,2,3}; 4 Class<?> c = temp.getClass().getComponentType(); //取得数组的Class实例 5 System.out.println(c.getName()); //输出数组的名称 6 System.out.println(Array.getLength(temp)); //取得数组的长度 7 System.out.println(Array.get(temp,0)); //取得数组的第一个内容 8 9 Array.set(temp,0,6); //修改数组第一个内容为6 10 } 11 }