概念:什麼是反射html
java反射機制: JAVA反射機制是在運行狀態中,java
對於任意一個類,都可以知道這個類的全部屬性和方法;數組
對於任意一個對象,都可以調用它的任意一個方法和屬性;ide
這種動態獲取的信息以及動態調用對象的方法的功能稱爲java語言的反射機制。函數
簡而言之: 就是根據一個已經實例化了的對象來還原類的完整信息this
案例1:經過反射修改屬性spa
package Test2016.demo; import java.lang.reflect.Field; public class Demo4 { public static void main(String[] args) throws Exception { Student stu = new Student(); Field[] fields = stu.getClass().getDeclaredFields(); for (Field f : fields) { f.setAccessible(true); //設置是否容許訪問,不寫運行會報錯 if (f.getName() == "name") { f.set(stu, "java"); } else if (f.getName() == "age") { f.set(stu, 20); } } System.out.println(stu); //輸出:java:20 } } class Student { private String name; private int age; public Student() { this.name = "zhangsan"; this.age = 10; } //重寫toString方法,不然輸出:Test2016.demo.Student@e53108 public String toString() { return this.name + ":" + this.age; } }
案例2:經過反射調用方法code
package Test2016.demo; import java.lang.reflect.Method; public class Demo4 { @SuppressWarnings("unchecked") public static void main(String[] args) throws Exception { Student stu = new Student("zhangsan", 21); Class c = stu.getClass(); //getMethod()方法須要傳入方法名和方法所帶參數的參數類型 Method method = c.getMethod("score", int.class); //invoke()表示調用的意思,須要傳入對象和參數 method.invoke(stu, 100); Method m = c.getMethod("say", String.class); //這裏的null表示不禁對象調用,也就是靜態方法,把null換位stu也是可行的 m.invoke(null, "hello java!!!"); } } class Student { private String name; private int age; public Student(String name, int age) { this.name = name; this.age = age; } public void score(int score) { System.out.println(this.name + " 考了 " + score + " 分"); } public static void say(String str) { System.out.println("剛纔我說了:" + str); } @Override public String toString() { return this.name + "-" + this.age; } }
程序輸出: zhangsan 考了 100 分
剛纔我說了:hello java!!!htm
案例3:經過反射操做數組對象
package Test2016.demo; import java.lang.reflect.Array; public class Demo4 { public static void main(String[] args) throws Exception { int[] arr = {1, 2, 3, 4, 5}; //getComponentType()返回你數組裏面裝的數據的數據類型的類名稱。這裏也就是int Class<?> c = arr.getClass().getComponentType(); System.out.println("數組類型:" + c.getName()); //數組類型:int int len = Array.getLength(arr); System.out.println("數組長度:" + len); //數組長度:5 System.out.print("遍歷數組:"); for (int i = 0; i < len; i++) { System.out.print(Array.get(arr, i) + " "); //遍歷數組:1 2 3 4 5 } System.out.println(); System.out.println("修改第三個數據前:" + Array.get(arr, 2)); //修改第三個數據前:3 Array.set(arr, 2, 10); System.out.println("修改第三個數據後:" + Array.get(arr, 2)); //修改第三個數據後:10 } }
注意點:
getFields()與getDeclaredFields()區別:
getFields()只能訪問類中聲明爲公有的字段,私有的字段它沒法訪問,能訪問從其它類繼承來的公有方法.
getDeclaredFields()能訪問類中全部的字段,與public,private,protect無關,不能訪問從其它類繼承來的方法
getMethods()與getDeclaredMethods()區別:
getMethods()只能訪問類中聲明爲公有的方法,私有的方法它沒法訪問,能訪問從其它類繼承來的公有方法.
getDeclaredFields()能訪問類中全部的字段,與public,private,protect無關,不能訪問從其它類繼承來的方法
getConstructors()與getDeclaredConstructors()區別:
getConstructors()只能訪問類中聲明爲public的構造函數.
getDeclaredConstructors()能訪問類中全部的構造函數,與public,private,protect無關