Java反射機制demo(三)—獲取類中的構造函數


Java反射機制demo(三)—獲取類中的構造函數 

1,獲取類中所有的構造函數

如下面的代碼中所示,這個類中顯式的構造函數有五個。

空構造:

  • public UserInfo()

帶參構造有四個:

  • public UserInfo(int userId)
  • private UserInfo(String name)
  • protected UserInfo(int userId, String name)
  • public UserInfo(int userId, String name, int age)

注意 他們的訪問修飾符。

 

 1 package com.aaron.reflect;
 2 
 3 public class UserInfo{
 4     private int userId;
 5     private String name;
 6     private int age;
 7     
 8     public UserInfo(){}
 9     
10     public UserInfo(int userId){
11         this.userId = userId;
12     }
13      private UserInfo(String name){
14          this.name = name;
15      }
16     
17     public UserInfo(int userId, String name, int age) {
18         super();
19         this.userId = userId;
20         this.name = name;
21         this.age = age;
22     }
23     
24     public int getUserId() {
25         return userId;
26     }
27     public void setUserId(int userId) {
28         this.userId = userId;
29     }
30     public String getName() {
31         return name;
32     }
33     public void setName(String name) {
34         this.name = name;
35     }
36     public int getAge() {
37         return age;
38     }
39     public void setAge(int age) {
40         this.age = age;
41     }
42     @Override
43     public String toString() {
44         return "UserInfo [userId=" + userId + ", name=" + name + ", age=" + age + "]";
45     }
46     
47 }

 

 

我們可以使用Class類中的Constuctor<?>[] getConstructors()方法,來獲得這個類的構造函數。

 JDK API文檔里,對這個方法的描述如下:

返回一個包含某些 Constructor 對象的數組,這些對象反映此 Class 對象所表示的類的所有公共構造方法。如果該類沒有公共構造方法,或者該類是一個數組類,或者該類反映一個基本類型或 void,則返回一個長度為 0 的數組。 注意,此方法返回 Constructor<T> 對象的數組(即取自此類構造方法的數組)時,此方法的返回類型是 Constructor<?>[]不是 預期的 Constructor<T>[]。此少量信息的返回類型是必需的,因為從此方法返回之后,該數組可能被修改以保存不同類的 Constructor 對象,而這將違反 Constructor<T>[] 的類型保證。

總之,返回了表示此類公共構造方法的Constructor對象數組。注意,這里是公共構造方法

測試類的代碼如下:

  

Constuctor<?>[] getConstructors()

package com.aaron.reflect;

import java.lang.reflect.Constructor;

public class Demo2 {
	public static void main(String[] args) {
		Class<?> c = UserInfo.class;//獲取Class對象
		
		Constructor<?> cons[] = c.getConstructors();//獲取構造函數的數組
		//打印
		for (Constructor<?> constructor : cons) {
			System.out.println(constructor);
		}
	}
}

運行結果如下:

public com.aaron.reflect.UserInfo()
public com.aaron.reflect.UserInfo(int,java.lang.String,int)
public com.aaron.reflect.UserInfo(int)

 運行的結果打印出了所有顯式聲明的,而且是公共的構造函數。

 但是,這個順序和我們類里的定義順序是不一樣的,因此,從這個方法精准地定位一個構造函數是不可取的。真的亂序的嗎?API里沒有提到。但是,另外一個方法的文檔中提到了。這個方法是

Constuctor<?>[] getDeclaredConstructors()

這個方法返回Constructor對象的一個數組,這些對象包含了Class對象所表示的類中的所有構造方法。它們分別是公共,保護,默認(包),和私有構造。

返回數組中的元素沒有排序,也沒有任何特定的順序。

如果該類存在一個默認構造方法,則它包含在返回的數組中。如果此Class對象表示一個接口,一個基本類型,一個數組類或者void,則這個方法返回一個長度為0的數組。

測試類:

package com.aaron.reflect;

import java.lang.reflect.Constructor;

public class Demo2 {
	public static void main(String[] args) {
		Class<?> c = UserInfo.class;//獲取Class對象
		
		Constructor<?> cons[] = c.getDeclaredConstructors();
		//打印
		for (Constructor<?> constructor : cons) {
			System.out.println(constructor);
		}
	}
}

  運行結果:

public com.aaron.reflect.UserInfo()
public com.aaron.reflect.UserInfo(int,java.lang.String,int)
public com.aaron.reflect.UserInfo(int)
private com.aaron.reflect.UserInfo(java.lang.String)
protected com.aaron.reflect.UserInfo(int,java.lang.String)

2,調用構造方法生成實例

Constructor<T> getConstructor(Class<?>... parameterTypes)

package com.aaron.reflect;

import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;

public class Demo2 {
	public static void main(String[] args) {
		Class<?> c = UserInfo.class;//獲取Class對象
		try {
			Constructor<?> constructor = c.getConstructor(int.class);//只有使用類字面常量才能夠獲取基本類型的Class對象
			UserInfo userInfo = (UserInfo) constructor.newInstance(1);//構造實例
			System.out.println(userInfo);
		} catch (Exception e) {
			e.printStackTrace();
		} 
	}
}

  注意其中的注釋,只有使用類字面常量才能獲得int這種基本類型的Class對象。

而Integer.class和int.class所表示的Class必然不同,因為一個是泛型一個是基本類型。Integer繼承了java.lang.Number,而Number繼承了java.lang.Object。

下面給出運行結果。

UserInfo [userId=1, name=null, age=0]

  

  


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM