Java反射

反射

Java反射機制是指在運行狀態中,對於任意一個類,都能夠知道這個類的所有屬性和方法;對於任意一個對象,都能夠調用它的任意一個方法和屬性;這種動態獲取的信息以及動態調用對象的方法的功能稱爲Java語言的反射機制。

反射是框架的靈魂,它可以有效地降低類之間的耦合,很多框架都運用了反射原理,例如hibernate 的實體類,Spring的AOP等等都有反射的實現。

獲取公共構造器 getConstructors()

獲取所有構造器 getDeclaredConstructors()

獲取該類對象 newInstance()

獲取類名包含包路徑 getName()

獲取類名不包含包路徑 getSimpleName()

獲取類公共類型的所有屬性 getFields()

獲取類的所有屬性 getDeclaredFields()

獲取類公共類型的指定屬性 getField(String name)

獲取類全部類型的指定屬性 getDeclaredField(String name)

獲取類公共類型的方法 getMethods()

獲取類的所有方法 getDeclaredMethods()

獲得類的特定公共類型方法: getMethod(String name, Class[] parameterTypes)

獲取內部類 getDeclaredClasses()

獲取外部類 getDeclaringClass()

獲取修飾符 getModifiers()

獲取所在包 getPackage()

獲取所實現的接口 getInterfaces()

反射

從圖中可以得出以下幾點:

Class 類的實例對象表示正在運行的 Java 應用程序中的類和接口。也就是jvm中有很多的實例,每個類都有唯一的Class對象。
Class 類沒有公共構造方法。Class 對象是在加載類時由 Java 虛擬機自動構造的。也就是說我們不需要創建,JVM已經幫我們創建了。
Class 對象用於提供類本身的信息,比如有幾種構造方法, 有多少屬性,有哪些普通方法

1、獲取類對象

獲取類對象有3種方式

Class.forName()(常用)

Hero.class

new Hero().getClass()

在一個JVM中,一種類,只會有一個類對象存在。所以以上三種方式取出來的類對象,都是一樣。(此處準確是在ClassLoader下,只有一個類對象)

三種方式中,常用第一種,第二種需要導入類的包,依賴太強,不導包就拋編譯錯誤。第三種對象都有了還要反射幹什麼。一般都第一種,一個字符串可以傳入也可寫在配置文件中等多種方法。

基本步驟

與傳統的通過new 來獲取對象的方式不同反射機制,反射會先拿到Hero的“類對象”,然後通過類對象獲取“構造器對象”再通過構造器對象創建一個對象,具體步驟:

1.獲取類對象 Class class = Class.forName(“pojo.Hero”);

2.獲取構造器對象 Constructor con = clazz.getConstructor(形參.class);

3 獲取對象 Hero hero =con.newInstance(實參);

2、獲取構造器對象方法

1).批量的方法:

public Constructor[] getConstructors():所有"公有的"構造方法

public Constructor[] getDeclaredConstructors():獲取所有的構造方法(包括私有、受保護、默認、公有)

2).獲取單個的方法:

public Constructor getConstructor(Class… parameterTypes): 獲取單個的"公有的"構造方法

public Constructor getDeclaredConstructor(Class…parameterTypes):獲取"某個構造方法"可以是私有的,或受保護、默認、公有;

3、獲取成員變量並使用

1.獲取HeroPlus類的對象 new方法/第2章中的方法 h

  1. 獲取屬性 Field f1 = h.getDeclaredField(“屬性名”)

  2. 修改屬性 f1.set(h,實參),注意這裏的h是對象,不是類對象

補充:

getField和getDeclaredField的區別

getField 只能獲取public的,包括從父類繼承來的字段。

getDeclaredField 可以獲取本類所有的字段,包括private的,但是 不能獲取繼承來的字段。 (注: 這裏只能獲取到private的字段,但並不能訪問該private字段的值,除非加上setAccessible(true))

4、獲取成員方法並使用

獲取HeroPlus類的對象 h

獲取成員方法:

public Method getMethod(String name ,Class<?>… parameterTypes):獲取"公有方法";(包含了父類的方法也包含Object類)

public Method getDeclaredMethods(String name ,Class<?>… parameterTypes) :獲取成員方法,包括私有的(不包括繼承的)

參數解釋:

name : 方法名;

Class … : 形參的Class類型對象

調用方法

Method --> public Object invoke(Object obj,Object… args):

參數說明:

obj : 要調用方法的對象;

args:調用方式時所傳遞的實參; 反射一般使用在框架中,框架需要很強的靈活性

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章