1. 程式人生 > 其它 >8.23Java反射訪問方法

8.23Java反射訪問方法

8.23Java反射訪問方法

獲取一個物件方法的資訊

動態獲取一個物件方法的資訊,首先需要通過下列方法之一建立一個 Method 型別的物件或者陣列。

  • getMethods()

  • getMethods(String name,Class<?> …parameterTypes)

  • getDeclaredMethods()

  • getDeclaredMethods(String name,Class<?>...parameterTypes)

例項:

objectClass.getDeclaredConstructor("max",int.class,String.class);
objectClass.getDeclaredConstructor("max",new Class[]{int.class,String.class});
靜態方法名稱說明
getName() 獲取該方法的名稱
getParameterType() 按照宣告順序以 Class 陣列的形式返回該方法各個引數的型別
getReturnType() 以 Class 物件的形式獲得該方法的返回值型別
getExceptionTypes() 以 Class 陣列的形式獲得該方法可能丟擲的異常型別
invoke(Object obj,Object...args) 利用 args 引數執行指定物件 obj 中的該方法,返回值為 Object 型別
isVarArgs() 檢視該方法是否允許帶有可變數量的引數,如果允許返回 true,否則返回 false
getModifiers() 獲得可以解析出該方法所採用修飾符的整數

目標類

package PracticeReview.Reflect;

public class ReflectPracticeDemoNo2 {
// static 作用域方法
static void staticMethod() {
System.out.println("執行staticMethod()方法");
}
// public 作用域方法
public int publicMethod(int i) {
System.out.println("執行publicMethod()方法");
return 100 + i;
}
// protected 作用域方法
protected int protectedMethod(String s, int i) throws NumberFormatException {
System.out.println("執行protectedMethod()方法");
return Integer.valueOf(s) + i;
}
// private 作用域方法
private String privateMethod(String... strings) {
System.out.println("執行privateMethod()方法");
StringBuffer sb = new StringBuffer();
for (int i = 0; i < sb.length(); i++) {
sb.append(strings[i]);
}
return sb.toString();
}
}

測試類:

package PracticeReview.Reflect;

import java.lang.reflect.Method;

public class ReflectTestNo2 {
public static void main(String[] args) {
// 獲取動態類ReflectPracticeDemoNo2
ReflectPracticeDemoNo2 book = new ReflectPracticeDemoNo2();
Class class1 = book.getClass();
// 獲取ReflectPracticeDemoNo2類的所有方法
Method[] declaredMethods = class1.getDeclaredMethods();
for (int i = 0; i < declaredMethods.length; i++) {
Method method = declaredMethods[i];
System.out.println("方法名稱為:" + method.getName());
System.out.println("方法是否帶有可變數量的引數:" + method.isVarArgs());
System.out.println("方法的引數型別依次為:");
// 獲取所有引數型別
Class[] methodType = method.getParameterTypes();
for (int j = 0; j < methodType.length; j++) {
System.out.println(" " + methodType[j]);
}
// 獲取返回值型別
System.out.println("方法的返回值型別為:" + method.getReturnType());
System.out.println("方法可能丟擲的異常型別有:");
// 獲取所有可能丟擲的異常
Class[] methodExceptions = method.getExceptionTypes();
for (int j = 0; j < methodExceptions.length; j++) {
System.out.println(" " + methodExceptions[j]);
}
boolean isTurn = true;
while (isTurn) {
try { // 如果該成員變數的訪問許可權為private,則丟擲異常
isTurn = false;
if (method.getName().equals("staticMethod")) { // 呼叫沒有引數的方法
method.invoke(book);
} else if (method.getName().equals("publicMethod")) { // 呼叫一個引數的方法
System.out.println("publicMethod(10)的返回值為:" + method.invoke(book, 10));
} else if (method.getName().equals("protectedMethod")) { // 呼叫兩個引數的方法
System.out.println("protectedMethod(\"10\",15)的返回值為:" + method.invoke(book, "10", 15));
} else if (method.getName().equals("privateMethod")) { // 呼叫可變數量引數的方法
Object[] parameters = new Object[] { new String[] { "J", "A", "V", "A" } };
System.out.println("privateMethod()的返回值為:" + method.invoke(book, parameters));
}
} catch (Exception e) {
System.out.println("在設定成員變數值時丟擲異常,下面執行setAccessible()方法");
method.setAccessible(true); // 設定為允許訪問private方法
isTurn = true;
}
}
System.out.println("=============================\n");
}
}
}

It's a lonely road!!!