java–反射原理及操作
- 2019 年 10 月 10 日
- 筆記
1、反射原理

反射具體操作
15、反射的原理(********理解********) * 應用在一些通用性比較高的程式碼 中 * 後面學到的框架,大多數都是使用反射來實現的 * 在框架開發中,都是基於配置文件開發 ** 在配置文件中配置了類,可以通過反射得到類中的 所有內容,可以讓類中的某個方法來執行 * 類中的所有內容:屬性、沒有參數的構造方法、有參數的構造方法、普通方法 * 畫圖分析反射的原理 * 首先需要把java文件保存到本地硬碟 .java * 編譯java文件,成.class文件 * 使用jvm,把class文件通過類載入載入到記憶體中 * 萬事萬物都是對象,class文件在記憶體中使用Class類表示 * 當使用反射時候,首先需要獲取到Class類,得到了這個類之後,就可以得到class文件裡面的所有內容 - 包含屬性 構造方法 普通方法 * 屬性通過一個類 Filed * 構造方法通過一個類 Constructor * 普通方法通過一個類 Method 16、使用反射操作類裡面的無參數的構造方法(**會寫**) * 首先獲取到Class類 - // 獲取Class類 Class clazz1 = Person.class; Class clazz2 = new Person().getClass(); Class clazz3 = Class.forName("cn.itcast.test09.Person"); * 比如: 要對一個類進行實例化,可以new,不使用new,怎麼獲取? - //得到Class Class c3 = Class.forName("cn.itcast.test09.Person"); //得到Person類的實例 Person p = (Person) c3.newInstance(); * 程式碼 //操作無參數的構造方法 @Test public void test1() throws Exception { //得到Class Class c3 = Class.forName("cn.itcast.test09.Person"); //得到Person類的實例 Person p = (Person) c3.newInstance(); //設置值 p.setName("zhangsan"); System.out.println(p.getName()); } 17、使用反射操作有參數的構造方法(**會寫**) //操作有參數的構造方法 @Test public void test2() throws Exception { //得到Class Class c1 = Class.forName("cn.itcast.test09.Person"); //使用有參數的構造方法 //c1.getConstructors();//獲取所有的構造方法 //傳遞是有參數的構造方法裡面參數類型,類型使用class形式傳遞 Constructor cs = c1.getConstructor(String.class,String.class); //通過有參數的構造方法設置值 //通過有參數的構造方法創建Person實例 Person p1 = (Person) cs.newInstance("lisi","100"); System.out.println(p1.getId()+" "+p1.getName()); } 18、使用反射操作屬性(**會寫**) * //操作name屬性 @Test public void test3() { try { //得到Class類 Class c2 = Class.forName("cn.itcast.test09.Person"); //得到name屬性 //c2.getDeclaredFields();//表示得到所有的屬性 //得到Person類的實例 Person p11 = (Person) c2.newInstance(); //通過這個方法得到屬性,參數是屬性的名稱 Field f1 = c2.getDeclaredField("name"); //操作的是私有的屬性,不讓操作,需要設置可以操作私有屬性setAccessible(true),可以操作私有屬性 f1.setAccessible(true); //設置name值 set方法,兩個參數:第一個參數類的實例,第二個參數是設置的值 f1.set(p11, "wangwu"); //相當於 在 p.name = "wangwu"; System.out.println(f1.get(p11)); //相當於 p.name }catch(Exception e) { e.printStackTrace(); } } 19、使用泛型操作普通方法(**會寫**) * 使用Method類表示普通方法 * 程式碼 //操作普通方法 ,比如操作 setName @Test public void test4() throws Exception { //得到Class類 Class c4 = Class.forName("cn.itcast.test09.Person"); //得到Person實例 Person p4 = (Person) c4.newInstance(); //得到普通方法 //c4.getDeclaredMethods();//得到所有的普通方法 //傳遞兩個參數:第一個參數,方法名稱;第二個參數,方法裡面參數的類型 Method m1 = c4.getDeclaredMethod("setName", String.class); //讓setName方法執行 ,執行設置值 //使用invoke(p4, "niuqi");傳遞兩個參數:第一個參數,person實例;第二個參數,設置的值 //執行了invoke方法之後,相當於,執行了setName方法,同時通過這個方法設置了一個值是niuqi m1.invoke(p4, "niuqi"); System.out.println(p4.getName()); } * //操作的私有的方法 ,需要設置值是true * //m1.setAccessible(true); * 當操作的方法是靜態的方法時候,因為靜態方法調用方式是 類名.方法名,不需要類的實例 * 使用反射操作靜態方式時候,也是不需要實例 * 在invokie方法的第一個參數裡面,寫一個 null - m1.invoke(null, "niuqi");