摘要:筆記來源反射綜述類的使用方法的反射成員變量的反射構(gòu)造函數(shù)的反射類加載機制類的使用在面向?qū)ο蟮氖澜缋铮f事萬物皆對象。
筆記來源:IMOOC 反射Java Reflect
Class 類的使用綜述
Class類的使用
方法的反射
成員變量的反射
構(gòu)造函數(shù)的反射
類加載機制
在面向?qū)ο蟮氖澜缋铮f事萬物皆對象。
但在Java里面有兩樣?xùn)|西不是對象:靜態(tài)的成員、普通數(shù)據(jù)類型類(但它們有封裝類彌補)
類是對象,類是 java.lang.Class 的實例對象(There is a class named Class)
package com.gcusky.reflect; class ClassDemo { Foo foo = new Foo(); // Foo的實例對象 /** * foo 是 Foo 類的實例對象 * Foo 是 Class 類的實例對象,又叫類類型(class type) */ // 表示1 -> 任何一個類都有一個隱含的靜態(tài)成員變量class Class c1 = Foo.class; // 表示2 -> 已知該類對象可用getClass方法獲取類類型 Class c2 = foo.getClass(); // 表示3 -> 用類的全稱獲取 try { Class c3 = Class.forName("com.gcusky.reflect.Foo"); } catch (ClassNotFoundException e) { e.printStackTrace(); } // 可以通過類的類類型創(chuàng)建該類的實例對象 try { Foo foo1 = (Foo)c1.newInstance(); } catch (InstantiationException e) { e.printStackTrace(); } catch (IllegalAccessException e) { e.printStackTrace(); } } class FooJava 動態(tài)加載類
Class.forName("類的全稱")
不僅表示了類的類類型,還代表了動態(tài)加載類
編譯時刻加載類是靜態(tài)加載類
運行時刻加載類是動態(tài)加載類
class Office { public static void main(String[] args) { // new 創(chuàng)建對象,是靜態(tài)加載類,在編譯時就需要加載所有可能使用到的類 if("Word".equals(args[0])) { Word w = new Word(); w.start(); } // Class.forName 創(chuàng)建對象,是動態(tài)加載類,在運行時才加載 try { Class c = Class.forName(args[0]) Word w = (Word) c.newInstance(); // 通過類類型,創(chuàng)建該對象 w.start(); } catch (Exception e) { e.printStackTrace(); } } }Java 獲取方法信息
基本的數(shù)據(jù)類型,void 關(guān)鍵字都存在類類型
java.lang.reflect.Method 封裝了關(guān)于方法的操作
package com.gcusky.reflect; import java.lang.reflect.Method; public class Demo { /** * 打印類的信息,包括類的成員函數(shù)、成員變量 * @param obj 對象 */ public static void printClassMessage(Object obj) { // 要獲取類的信息,首先要獲取類的類類型 Class c = obj.getClass(); // 獲取類的全名 String fullName = c.getName(); /** * Method類:方法對象 * 一個成員方法就是一個Method對象 * getMethods()方法獲取的是所有的public的函數(shù),包括父類繼承而來的 * getDeclaredMethods() 獲取的是所有該類自己聲明的方法,不問訪問權(quán)限 */ Method[] ms = c.getMethods(); // c.getDeclaredMethods(); for (int i = 0; i < ms.length; i++) { // 得到方法的返回類型 Class returnType = ms[i].getReturnType(); // 得到方法的名稱 String name = ms[i].getName(); // 獲取參數(shù)類型 Class[] paramTypes = ms[i].getParameterTypes(); } } }Java 獲取成員變量信息
成員變量也是對象
java.lang.reflect.Field 封裝了關(guān)于成員變量的操作
/** * 成員變量也是對象,F(xiàn)ield封裝了關(guān)于成員變量的操作 * getFields()獲取的是所有的public的成員變量 * getDeclaredMethods()獲取的是所有該類自己聲明的成員變量 */ Field[] fs = c.getDeclaredFields(); // c.getFields(); for (int i = 0; i < fs.length; i++) { // 得到成員變量的類型 Class fieldType = fs[i].getType(); String typeName = fieldType.getName(); // 得到成員變量的名稱 String fieldName = fs[i].getName(); }Java 獲取構(gòu)造函數(shù)信息
/** * 構(gòu)造函數(shù)也是對象 * java.lang.Constructor中封裝了構(gòu)造函數(shù)的信息 */ Constructor[] cs = c.getDeclaredConstructors(); for (Constructor constructor : cs) { constructor.getName(); Class[] paramType = constructor.getParameterTypes(); }Java 方法的反射
如何獲取某個方法:方法的名稱和方法的參數(shù)列表才能唯一決定某個方法
方法反射的操作:method.invoke(對象, 參數(shù)列表)
class A { public void print(int a, int b) { System.out.println(a + b); } } A a = new A(); Class c = a.getClass(); try { // Method m = c.getMethod("print", new Class[]{int.class, int.class}); Method m = c.getMethod("print", int.class, int.class); // Object o = m.invoke(a, new Object[]{10, 20}); Object o = m.invoke(a, 10, 20); } catch (Exception e) { e.printStackTrace(); }Java 類加載機制
ArrayList list = new ArrayList(); ArrayListlist1 = new ArrayList (); list == list1; // true list1.add(20); // error - 編譯檢測出錯
反射都是編譯之后的操作,因此可看出泛型在編譯之后會被擦除
Java 中集合的泛型用于防止錯誤輸入,只在編譯階段有效,繞過編譯則無效
Class c = list1.getclass(); try { Method m = c.getMethod("add", Object.class); m.invoke(list1, 20); // correct - 繞過編譯操作就繞過了泛型 } catch (Exception e) { e.printStackTrace(); }
參考資料:
先有Class還是先有Object?
Scala Reflection - Mirrors,ClassTag,TypeTag and WeakTypeTag
文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請注明本文地址:http://specialneedsforspecialkids.com/yun/69142.html
摘要:當(dāng)某個類型變量只在整個參數(shù)列表的所有參數(shù)和返回值中的一處被應(yīng)用了,那么根據(jù)調(diào)用方法時該處的實際應(yīng)用類型來確定。即直接根據(jù)調(diào)用方法時傳遞的參數(shù)類型或返回值來決定泛型參數(shù)的類型。 標(biāo)簽: java [TOC] 本文對泛型的基本知識進行較為全面的總結(jié),并附上簡短的代碼實例,加深記憶。 泛型 將集合中的元素限定為一個特定的類型。 術(shù)語 ArrayList -- 泛型類型 ArrayLis...
摘要:知識點總結(jié)反射反射操作泛型知識點總結(jié)反射采用泛型擦除的機制來引入泛型。中的泛型僅僅是給編譯器使用的,確保數(shù)據(jù)的安全性和免去強制類型轉(zhuǎn)換的麻煩。 Java知識點總結(jié)(反射-反射操作泛型) @(Java知識點總結(jié))[Java, 反射] Java采用泛型擦除的機制來引入泛型。Java中的泛型僅僅是給編譯器javac使用的, 確保數(shù)據(jù)的安全性和免去強制類型轉(zhuǎn)換的麻煩 。但是,__一旦編譯完成,...
摘要:構(gòu)造器創(chuàng)建實例構(gòu)造器和方法的反射類不同點在于,可以創(chuàng)建實例,代碼如下所示。 上一篇文章介紹了反射的基本概念以及獲取類相關(guān)信息的反射API,這一章節(jié)主要記錄如何對類的成員進行操作的相關(guān)反射API。 操作類成員的類 反射API中提供了如下接口,用于對類的成員進行操作。 java.lang.reflect.Member 該接口主要有以下三個實現(xiàn)類,用于對類成員中的字段,方法和構(gòu)造器進行操作...
摘要:哪吒社區(qū)技能樹打卡打卡貼函數(shù)式接口簡介領(lǐng)域優(yōu)質(zhì)創(chuàng)作者哪吒公眾號作者架構(gòu)師奮斗者掃描主頁左側(cè)二維碼,加入群聊,一起學(xué)習(xí)一起進步歡迎點贊收藏留言前情提要無意間聽到領(lǐng)導(dǎo)們的談話,現(xiàn)在公司的現(xiàn)狀是碼農(nóng)太多,但能獨立帶隊的人太少,簡而言之,不缺干 ? 哪吒社區(qū)Java技能樹打卡?【打卡貼 day2...
摘要:反射機制是什么反射機制是在運行狀態(tài)中,對于任意一個類,都能夠知道這個類的所有屬性和方法對于任意一個對象,都能夠調(diào)用它的任意一個方法和屬性這種動態(tài)獲取的信息以及動態(tài)調(diào)用對象的方法的功能稱為語言的反射機制反射機制能做什么反射機制主要提供了以下功 反射機制是什么 反射機制是在運行狀態(tài)中,對于任意一個類,都能夠知道這個類的所有屬性和方法;對于任意一個對象,都能夠調(diào)用它的任意一個方法和屬性;這種...
閱讀 3280·2023-04-26 02:09
閱讀 2574·2021-11-24 09:39
閱讀 3268·2021-11-16 11:52
閱讀 3614·2021-10-26 09:50
閱讀 2771·2021-10-08 10:05
閱讀 2456·2021-09-22 15:25
閱讀 3299·2019-08-30 13:14
閱讀 908·2019-08-29 17:06