Java通過反射API操作:構造器、方法、屬性
阿新 • • 發佈:2018-12-17
一 測試各種型別的(class,interface, enum, annotation, primitive, type, void)對應的java.lang.Class物件的獲取方式
package Reflection; /** * 測試各種型別的(class,interface, enum, annotation, primitive, type, void)對應的java.lang.Class物件的獲取方式 * @author lenovo * */ public class TestClass { public static void main(String[] args) { String path = "Reflection.User"; //要載入類的地址 try { //物件表示或封裝一些資料,一個類被載入後,JVM會建立一個對應該類的Class物件,類的整個結構資訊會被放到對應的Class物件中。 //這個Class物件就像一面鏡子一樣,通過這面鏡子我可以看到對應類的全部資訊 Class clazz = Class.forName(path); //載入類的內容 System.out.println(clazz); Class strClazz = String.class; System.out.println(strClazz); Class strClazz2 = path.getClass(); //發現String.class和path.getClass()獲得的是同一個物件 System.out.println(strClazz == strClazz2); Class intClazz = int.class; System.out.println(intClazz); } catch (Exception e) { e.printStackTrace(); } } }
User:
package Reflection; public class User { private int id; private int age; private String uname; public int getId() { return id; } public void setId(int id) { this.id = id; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } public String getUname() { return uname; } public void setUname(String uname) { this.uname = uname; } public User(int id, int age, String uname) { super(); this.id = id; this.age = age; this.uname = uname; } //javabean必須要有無參建構函式 public User() { super(); } public static void main(String[] args) { } }
二 利用反射的API,獲取類的資訊(類的名字、屬性、方法、構造器等)
package Reflection; import java.lang.reflect.Constructor; import java.lang.reflect.Field; import java.lang.reflect.Method; /** * 利用反射的API,獲取類的資訊(類的名字、屬性、方法、構造器等) * @author lenovo * */ public class ReflectionAPI { public static void main(String[] args) { String path = "Reflection.User"; //要載入類的地址 try { Class clazz = Class.forName(path); //載入類的內容 //獲取類的名字 System.out.println(clazz.getName()); //獲得全路徑即包名+類名:Reflection.User System.out.println(clazz.getSimpleName()); //獲得類名:User //獲取屬性資訊 // Field[] fields = clazz.getFields(); //只能獲得public的field Field[] fields = clazz.getDeclaredFields(); //獲得全部屬性 for(Field temp: fields) { System.out.println("屬性:" + temp); } //獲得方法資訊 Method[] methods = clazz.getDeclaredMethods(); Method m1 = clazz.getDeclaredMethod("getUname", null); //如果有引數,則必須傳遞引數型別對應的class物件 Method m2 = clazz.getDeclaredMethod("setUname", String.class); for(Method temp: methods) { System.out.println("方法:" + temp); } //獲得構造器資訊 Constructor[] constructors = clazz.getDeclaredConstructors(); for(Constructor temp: constructors) { System.out.println("構造器:" + temp); } //獲取制定型別的構造器 Constructor c = clazz.getDeclaredConstructor(int.class, int.class, String.class); System.out.println("獲得本類的建構函式:" + c); } catch (Exception e) { e.printStackTrace(); } } }
三 通過反射API動態操作:構造器、方法、屬性
package Reflection;
import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
/**
* 通過反射API動態操作:構造器、方法、屬性
* @author lenovo
*
*/
public class ReflectionAPIUse {
public static void main(String[] args) {
String path = "Reflection.User"; //要載入類的地址
try {
Class<User> clazz = (Class<User>) Class.forName(path); //載入類的內容
//通過反射API動態呼叫構造方法,構造物件
User u = clazz.newInstance(); //實質是呼叫User的無參構造方法建立物件
System.out.println(u);
//動態呼叫有參建構函式
Constructor<User> c = clazz.getDeclaredConstructor(int.class, int.class, String.class);
User u2 = c.newInstance(001, 123, "王建");
System.out.println(u2.getUname());
//通過反射API呼叫普通的方法
User u3 = clazz.newInstance();
Method method = clazz.getDeclaredMethod("setUname", String.class);
method.invoke(u3, "wangjian"); //上面兩行等價於u3.setUname("wangjian")
System.out.println(u3.getUname());
//通過反射API操作屬性
User u4 = clazz.newInstance();
Field f = clazz.getDeclaredField("uname");
f.setAccessible(true); //這個屬性不需要做安全檢查了,可以直接訪問
f.set(u4, "計算機小白"); //通過反射寫屬性的值
System.out.println(u4.getUname()); //通過反射直接讀屬性的值
} catch (Exception e) {
e.printStackTrace();
}
}
}