『壹』 java中反射是什麼
JAVA中反射是動態獲取信息以及動態調用對象方法的一種反射機制。
Java反射就是在運行狀態中,對於任意一個類,都能夠知道這個類的所有屬性和方法;對於任意一個對象,都能夠調用它的任意方法和屬性;並且能改變它的屬性。而這也是Java被視為動態語言的一個關鍵性質。
Java反射的功能是在運行時判斷任意一個對象所屬的類,在運行時構造任意一個類的對象,在運行時判斷任意一個類所具有的成員變數和方法,在運行時調用任意一個對象的方法,生成動態代理。
(1)java反射執行擴展閱讀:
JAVA中反射實例:
1、Class superClass=clazz.getSuperclass();//獲取父類。
System.out.println("getSuperclass:"+superClass)。
2、Class[] interfaces=clazz.getInterfaces();//獲取實現介面。
System.out.println("getInterfaces:"+interfaces.length)。
3、Constructor[] cons=clazz.getConstructors();//構造方法。
System.out.println("getConstructors:"+cons.length)。
參考資料來源:網路: JAVA反射機制
『貳』 Java的反射機制是什麼,如何實現
Java中的反射機制,通俗點解釋就是能夠在程序運行中動態獲取到內存中任一對象的信息,這些信息包括對象所屬類、類中的方法和屬性、以及它們的訪問控制域和返回值類型等等,還可以通過反射動態調用對象中的方法,而不管該方法的訪問域是私有或是公開,包括構造方法,還能實現動態代理等。總之,反射能夠破壞掉JAVA類本身的封裝性,進而獲取其私有的或公開的信息,也就能突破封裝進而調用私有的或公開的方法。
實現的話就是通過反射介面,JAVA把反射相關的類介面都封裝在了java.lang.reflect這個包中,你可以研究下這個包中的類,對於類的每一個屬性,如變數、方法,構造方法,這個包中都就與之相對應的類,通過這個類就可以操作這個屬性了。
java反射很強大,但也很危險,在實際開發中應少用或不用,在必要用之時,往往也能解決你遇到的問題。
『叄』 關於用java反射調用一個類裡面的方法並執行
Java中要用到反射,首先就必須要獲取到對應的class對象,在Java中有三種方法獲取類對應的class對象。
1、通過類的.class屬性
2、通過類實例的getClass()方法獲取
3、通過Class.forName(String className)方法獲取
現在比如在package下有個類Calculator
publicclassCalculator{
publicdoubleadd(doublescore1,doublescore2){
returnscore1+score2;
}
publicvoidprint(){
System.out.println("OK");
}
publicstaticdoublemul(doublescore1,doublescore2){
returnscore1*score2;
}
}
publicclassCalculatorTest{
publicstaticvoidmain(String[]args)throwsException{
//通過類的.class屬性獲取
Class<Calculator>clz=Calculator.class;
//或者通過類的完整路徑獲取,這個方法由於不能確定傳入的路徑是否正確,這個方法會拋ClassNotFoundException
// Class<Calculator>clz=Class.forName("test.Calculator");
//或者new一個實例,然後通過實例的getClass()方法獲取
// Calculators=newCalculator();
// Class<Calculator>clz=s.getClass();
//1.獲取類中帶有方法簽名的mul方法,getMethod第一個參數為方法名,第二個參數為mul的參數類型數組
Methodmethod=clz.getMethod("mul",newClass[]{double.class,double.class});
//invoke方法的第一個參數是被調用的對象,這里是靜態方法故為null,第二個參數為給將被調用的方法傳入的參數
Objectresult=method.invoke(null,newObject[]{2.0,2.5});
//如果方法mul是私有的private方法,按照上面的方法去調用則會產生異常NoSuchMethodException,這時必須改變其訪問屬性
//method.setAccessible(true);//私有的方法通過發射可以修改其訪問許可權
System.out.println(result);//結果為5.0
//2.獲取類中的非靜態方法
Methodmethod_2=clz.getMethod("add",newClass[]{double.class,double.class});
//這是實例方法必須在一個對象上執行
Objectresult_2=method_2.invoke(newCalculator(),newObject[]{2.0,2.5});
System.out.println(result_2);//4.5
//3.獲取沒有方法簽名的方法print
Methodmethod_3=clz.getMethod("print",newClass[]{});
Objectresult_3=method_3.invoke(newCalculator(),null);//result_3為null,該方法不返回結果
}
}
『肆』 北大青鳥java培訓:JAVA反射機制原理
運行時類型識別(Run-timeTypeIdentification,RTTI)主要有兩種方式,一種是我們在編譯時和運行時已經知道了所有的類型,另外一種是功能強大的「反射」機制。
要理解RTTI在Java中的工作原理,首先必須知道類型信息在運行時是如何表示的,這項工作是由「Class對象」完成的,它包含了與類有關的信息。
類是程序的重要組成部分,每個類都有一個Class對象,每當編寫並編譯了一個新類就會產生一個Class對象,它被保存在一個同名的.class文件中。
在運行時,當我們想生成這個類的對象時,運行這個程序的Java虛擬機(JVM)會確認這個類的Class對象是否已經載入,如果尚未載入,JVM就會根據類名查找.class文件,並將其載入,一旦這個類的Class對象被載入內存,它就被用來創建這個類的所有對象。
一般的RTTI形式包括三種:1.傳統的類型轉換。
如「(Apple)Fruit」,由RTTI確保類型轉換的正確性,如果執行了一個錯誤的類型轉換,就會拋出一個ClassCastException異常。
2.通過Class對象來獲取對象的類型。
如Classc=Class.forName(「Apple」);Objecto=c.newInstance();3.通過關鍵字instanceof或Class.isInstance()方法來確定對象是否屬於某個特定類型的實例,准確的說,應該是instanceof/Class.isInstance()可以用來確定對象是否屬於某個特定類及其所有基類的實例,這和equals()/==不一樣,它們用來比較兩個對象是否屬於同一個類的實例,沒有考慮繼承關系。
反射如果不知道某個對象的類型,可以通過RTTI來獲取,但前提是這個類型在編譯時必須已知,這樣才能使用RTTI來識別。
即在編譯時,編譯器必須知道所有通過RTTI來處理的類。
使用反射機制可以不受這個限制,它主要應用於兩種情況,第一個是「基於構件的編程」,在這種編程方式中,將使用某種基於快速應用開發(RAD)的應用構建工具來構建項目。
這是現在最常見的可視化編程方法,通過代表不同組件的圖標拖動到圖板上來創建程序,然後設置構件的屬性值來配置它們。
這種配置要求構件都是可實例化的,並且要暴露其部分信息,使得程序員可以讀取和設置構件的值。
當處理GUI時間的構件時還必須暴露相關方法的細細,以便RAD環境幫助程序員覆蓋這些處理事件的方法。
在這里,就要用到反射的機制來檢查可用的方法並返回方法名。
Java通過JavaBeans提供了基於構件的編程架構。
第二種情況,在運行時獲取類的信息的另外一個動機,就是希望能夠提供在跨網路的遠程平台上創建和運行對象的能力。
這被成為遠程調用(RMI),它允許一個Java程序將對象分步在多台機器上,江蘇java培訓http://www.kmbdqn.cn/認為這種分步能力將幫助開發人員執行一些需要進行大量計算的任務,充分利用計算機資源,提高運行速度。
『伍』 利用JAVA反射技術執行一個類的方法
public class Test {
public Test() {
}
public static void main(String[] args) throws IllegalArgumentException,
SecurityException, IllegalAccessException,
InvocationTargetException, NoSuchMethodException {
Bean bean = new Bean();
System.out.println(bean);
Bean.class.getMethod("setName", String.class).invoke(bean, "Jerry");
Bean.class.getMethod("setAge", int.class).invoke(bean, 25);
System.out.println("After reflection....\n" + bean);
}
}
class Bean {
private String name;
private int age;
public Bean() {
}
public Bean(String name, int age) {
super();
this.name = name;
this.age = age;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
public String toString() {
return "NAME: " + this.getName() + "\nAGE: " + this.getAge();
}
}
『陸』 JAVA中反射的應用
importjava.lang.reflect.*;publicclassTestClass{publicstaticvoidmain(String[]args)throwsException{/*Classc=Class.forName("Student");Field[]fs=c.getDeclaredFields();System.out.println("class"+c.getSimpleName()+"{");for(Fieldf:fs){System.out.println(f.getType().getSimpleName()+""+f.getName()+";");}Method[]ms=c.getDeclaredMethods();for(Methodm:ms){System.out.print(m.getReturnType().getSimpleName()+"");System.out.print(m.getName()+"(");Class[]ps=m.getParameterTypes();for(Classp:ps){System.out.print(p.getSimpleName()+",");}System.out.println("){}");}Constructor[]cons=c.getConstructors();for(Constructorcon:cons){System.out.println(c.getSimpleName()+"(");Class[]ps=con.getParameterTypes();for(Classp:ps){System.out.print(p.getSimpleName()+",");}System.out.println("){}");}*/Objects=newStudent("chun",18);Classc=s.getClass();Field[]fs=c.getDeclaredFields();for(Fieldf:fs){f.setAccessible(true);System.out.println(f.getName()+"="+f.get(s));//f.set(s,"123");//System.out.println(f.getName()+"="+f.get(s));}Class[]ps={};//無參數Methodm=c.getDeclaredMethod("study",ps);Object[]os={};m.invoke(s);/*Class[]ps={String.class,int.class};//有參數Methodm=c.getDeclaredMethod("study",ps);//說明是哪個方法Object[]os={"CoreJava",newInteger(3)};//簡單類型變成包裝類;m.invoke(s,os);*/}}classStudent{privateStringname;privateintage;publicStudent(){}publicStudent(Stringname,intage){this.name=name;this.age=age;}publicvoidsetName(Stringname){this.name=name;}publicvoidsetAge(intage){this.age=age;}publicvoidstudy(){System.out.println("Student"+name+"study1");}publicStringstudy(Stringcourse,inttime){System.out.println("Student"+name+"studies"+course+"for"+time+"times");if(time>=3)return"good";elsereturn"bad";}}這是我們當時學反射的時候打的代碼屬性方法構造方法都有
『柒』 java反射機制的實現原理
反射機制就是java語言在運行時擁有一項自觀的能力。
通過這種能力可以徹底的了解自身的情況為下一步的動作做准備。
下面具體介紹一下java的反射機制。這里你將顛覆原來對java的理解。
Java的反射機制的實現要藉助於4個類:class,Constructor,Field,Method;
其中class代表的時類對象,
Constructor-類的構造器對象,
Field-類的屬性對象,
Method-類的方法對象。
通過這四個對象我們可以粗略的看到一個類的各個組成部分。
Class:程序運行時,java運行時系統會對所有的對象進行運行時類型的處理。
這項信息記錄了每個對象所屬的類,虛擬機通常使用運行時類型信息選擇正 確的方法來執行(摘自:白皮書)。
但是這些信息我們怎麼得到啊,就要藉助於class類對象了啊。
在Object類中定義了getClass()方法。我 們可以通過這個方法獲得指定對象的類對象。然後我們通過分析這個對象就可以得到我們要的信息了。
比如:ArrayList arrayList;
Class clazz = arrayList.getClass();
然後我來處理這個對象clazz。
當然了Class類具有很多的方法,這里重點將和Constructor,Field,Method類有關系的方法。
Reflection 是 Java 程序開發語言的特徵之一,它允許運行中的 Java 程序對自身進行檢查,或者說「自審」,並能直接操作程序的內部屬性。Java 的這一能力在實際應用中也許用得不是很多,但是個人認為要想對java有個更加深入的了解還是應該掌握的。
reflection的工作機制
考慮下面這個簡單的例子,讓我們看看 reflection 是如何工作的。
import java.lang.reflect.*;
public class DumpMethods {
public static void main(String args[]) {
try {
//forName("java.lang.String")獲取指定的類的對象
Class c = Class.forName("java.lang.String");
Method m[] = c.getDeclaredMethods();
for (int i = 0; i < m.length; i++)
System.out.println(m[i].toString());
} catch (Throwable e) {
System.err.println(e);
}
}
}
按如下語句執行:
java DumpMethods java.util.ArrayList
這個程序使用 Class.forName 載入指定的類,然後調用 getDeclaredMethods 來獲取這個類中定義了的方法列表。java.lang.reflect.Methods 是用來描述某個類中單個方法的一個類。
Java類反射中的主要方法
對於以下三類組件中的任何一類來說
-- 構造函數、欄位和方法
-- java.lang.Class 提供四種獨立的反射調用,以不同的方式來獲得信息。調用都遵循一種標准格式。以下是用於查找構造函數的一組反射調用:
Constructor getConstructor(Class[] params) -- 獲得使用特殊的參數類型的公共構造函數,
Constructor[] getConstructors() -- 獲得類的所有公共構造函數
Constructor getDeclaredConstructor(Class[] params) -- 獲得使用特定參數類型的構造函數(與接入級別無關)
Constructor[] getDeclaredConstructors() -- 獲得類的所有構造函數(與接入級別無關)
獲得欄位信息的Class 反射調用不同於那些用於接入構造函數的調用,在參數類型數組中使用了欄位名:
Field getField(String name) -- 獲得命名的公共欄位
Field[] getFields() -- 獲得類的所有公共欄位
Field getDeclaredField(String name) -- 獲得類聲明的命名的欄位
Field[] getDeclaredFields() -- 獲得類聲明的所有欄位
用於獲得方法信息函數:
Method getMethod(String name, Class[] params) -- 使用特定的參數類型,獲得命名的公共方法
Method[] getMethods() -- 獲得類的所有公共方法
Method getDeclaredMethod(String name, Class[] params) -- 使用特寫的參數類型,獲得類聲明的命名的方法
Method[] getDeclaredMethods() -- 獲得類聲明的所有方法
使用 Reflection:
用於 reflection 的類,如 Method,可以在 java.lang.relfect 包中找到。使用這些類的時候必須要遵循三個步驟:
第一步是獲得你想操作的類的 java.lang.Class 對象。
在運行中的 Java 程序中,用 java.lang.Class 類來描述類和介面等。
下面就是獲得一個 Class 對象的方法之一:
Class c = Class.forName("java.lang.String");
這條語句得到一個 String 類的類對象。還有另一種方法,如下面的語句:
Class c = int.class;
或者
Class c = Integer.TYPE;
它們可獲得基本類型的類信息。其中後一種方法中訪問的是基本類型的封裝類 (如 Intege ) 中預先定義好的 TYPE 欄位。
第二步是調用諸如 getDeclaredMethods 的方法,以取得該類中定義的所有方法的列表。
一旦取得這個信息,就可以進行第三步了——使用 reflection API 來操作這些信息,如下面這段代碼:
Class c = Class.forName("java.lang.String");
Method m[] = c.getDeclaredMethods();
System.out.println(m[0].toString());
它將以文本方式列印出 String 中定義的第一個方法的原型。
處理對象:
a.創建一個Class對象
b.通過getField 創建一個Field對象
c.調用Field.getXXX(Object)方法(XXX是Int,Float等,如果是對象就省略;Object是指實例).
例如:
import java.lang.reflect.*;
import java.awt.*;
class SampleGet {
public static void main(String[] args) throws Exception {
Rectangle r = new Rectangle(100, 325);
printHeight(r);
printWidth( r);
}
static void printHeight(Rectangle r)throws Exception {
//Field屬性名
Field heightField;
//Integer屬性值
Integer heightValue;
//創建一個Class對象
Class c = r.getClass();
//.通過getField 創建一個Field對象
heightField = c.getField("height");
//調用Field.getXXX(Object)方法(XXX是Int,Float等,如果是對象就省略;Object是指實例).
heightValue = (Integer) heightField.get(r);
System.out.println("Height: " + heightValue.toString());
}
static void printWidth(Rectangle r) throws Exception{
Field widthField;
Integer widthValue;
Class c = r.getClass();
widthField = c.getField("width");
widthValue = (Integer) widthField.get(r);
System.out.println("Height: " + widthValue.toString());
}
}
『捌』 Java如何接收使用反射執行方法所返回的值
importjava.lang.reflect.Constructor;
importjava.lang.reflect.Method;
publicclassReflectDemo{
publicstaticvoidmain(String[]args)throwsException{
//獲取位元組碼文件對象
Classc=Class.forName("cn.itcast_01.Person");
//獲取所有的方法
//Method[]methods=c.getMethods();//獲取自己的包括父親的公共方法
//Method[]methods=c.getDeclaredMethods();//獲取自己的所有的方法
//for(Methodmethod:methods){
//System.out.println(method);
//}
Constructorcon=c.getConstructor();
Objectobj=con.newInstance();
/*
*Personp=newPerson();p.show();
*/
//獲取單個方法並使用
//publicvoidshow()
//publicMethodgetMethod(Stringname,Class<?>...parameterTypes)
//第一個參數表示的方法名,第二個參數表示的是方法的參數的class類型
Methodm1=c.getMethod("show");
//obj.m1();//錯誤
//publicObjectinvoke(Objectobj,Object...args)
//返回值是Object接收,第一個參數表示對象是誰,第二參數表示調用該方法的實際參數
m1.invoke(obj);//調用obj對象的m1方法
System.out.println("----------");
//publicvoidmethod(Strings)
Methodm2=c.getMethod("method",String.class);
m2.invoke(obj,"hello");
System.out.println("----------");
//publicStringgetString(Strings,inti)
Methodm3=c.getMethod("getString",String.class,int.class);
ObjectobjString=m3.invoke(obj,"hello",100);
System.out.println(objString);
//Strings=(String)m3.invoke(obj,"hello",100);
//System.out.println(s);
System.out.println("----------");
//privatevoidfunction()
Methodm4=c.getDeclaredMethod("function");
m4.setAccessible(true);
m4.invoke(obj);
}
}
『玖』 java 反射 方法調用
JAVA反射機制是在運行狀態中,對於任意一個類,都能夠知道這個類的所有屬性和方法;對於任意一個對象,都能夠調用它的任意一個方法和屬性;這種動態獲取的信息以及動態調用對象的方法的功能稱為java語言的反射機制。
JAVA反射(放射)機制:「程序運行時,允許改變程序結構或變數類型,這種語言稱為動態語言」。從這個觀點看,Perl,Python,Ruby是動態語言,C++,Java,C#不是動態語言。但是JAVA有著一個非常突出的動態相關機制:Reflection,用在Java身上指的是我們可以於運行時載入、探知、使用編譯期間完全未知的classes。換句話說,Java程序可以載入一個運行時才得知名稱的class,獲悉其完整構造(但不包括methods定義),並生成其對象實體、或對其fields設值、或喚起其methods。
說白了就是調用這個累的.Class方法然後調用其屬性和方法。