Java 反射
Class 類類型
理解java反射,有助於深入理解java面向對象思想,即萬事萬物皆對象(除了基本數據類型和靜態成員變量)
- 類是對象,是 java.lang.Class 的對象,稱 Class 爲類的類類型
- 方法是對象,是 java.lang.reflect.Method 的對象
- 成員變量是對象,是 import java.lang.reflect.Field 的對象
- 構造方法是對象, 是 java.lang.reflect.Constructor 的對象
- void 也是對象
獲取類類型的三種方法
// 1、通過.class方式獲取
Class c1 = User.class;
// 2、通過對象獲取
User user = new User();
Class c2 = user.getClass();
// 3、通過類路徑獲取
Class c3 = null;
try {
c3 = Class.forName("com.reflact.bean.User");
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
動態加載類及使用類類型創建對象
new方式在編譯時加載所有可能用到的類(靜態加載類),如果存在一個使用到的類未聲明,則編譯報錯,而編譯通過所加載的類不一定都會被用到
而動態加載類在編譯時不加載所有類,而在編譯後加載類,如果存在一個使用到的類未聲明,則編譯不會報錯,可以在用到時加載
Class c = null;
User u = null;
try {
// 動態加載類
c = Class.forName("com.reflact.bean.User");
// 使用類類型創建對象
u = (User) c.newInstance();
} catch (ClassNotFoundException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (InstantiationException e) {
e.printStackTrace();
}
使用類類型獲取該類的信息
類名
c.getName()
方法對象(方法名、返回值的類類型、參數的類類型)
Method[] methods = c.getMethods(); // 所有的
// Method[] methods = c1.getDeclaredMethods(); // 獲取自己的方法,不包含繼承而來的
for(int i = 0, j = methods.length; i < j; i++){
// 方法名
System.out.println(methods[i]);
// 返回值的類類型
System.out.println(methods[i].getReturnType());
// 參數的類類型
Class[] params = methods[i].getParameterTypes();
}
成員變量對象(類類型)
// Field[] fields = c1.getFields(); // public 的
Field[] fields = c.getDeclaredFields(); // 所有的
for(int i = 0, j = fields.length; i < j; i++){
// 成員變量名
System.out.println(fields[i].getName());
// 成員變量類類型
System.out.println(fields[i].getType());
}
構造方法對象(方法名、參數的類類型)
Constructor[] constructors = c.getConstructors();
for(int i = 0, j = constructors.length; i < j; i++){
// 參數的類類型
Class[] params = constructors[i].getParameterTypes();
}
方法的反射操作
Method method = null;
try {
// 根據方法名和參數列表類類型,使用該類類型獲取到某一方法,傳入方法名和參數類類型列表
method = c.getMethod("setUserName", String.class);
// 反射操作,傳入對象實例和參數列表
method.invoke(u, "Franco Liang");
} catch (NoSuchMethodException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
}