從 Java 中的字符串獲取類類型
一、概述
Class
類在 Java 反射中起著重要作用,因為它是所有反射操作的入口點。
在本快速教程中,我們將探索如何從字符串中的類名獲取Class
對象。
二、問題介紹
首先,讓我們創建一個簡單的類作為示例:
package com.baeldung.getclassfromstr;
public class MyNiceClass {
public String greeting(){
return "Hi there, I wish you all the best!";
}
}
如上面的代碼所示, MyNiceClass
類是在包com.baeldung.getclassfromstr
中創建的。此外,該類只有一個方法greeting(),
它返回一個String
。
我們的目標是從其名稱中獲取MyNiceClass
類的Class
對象。此外,我們想從Class
對象創建一個MyNiceClass
的實例,以驗證Class
對像是否是我們想要的對象。
為簡單起見,我們將使用單元測試斷言來驗證我們的解決方案是否按預期工作。
接下來,讓我們看看它的實際效果。
3.使用forName()
方法獲取Class
對象
Class
類提供了forName()
方法來從類名中獲取Class
對像作為字符串。接下來,我們看看如何調用方法來獲取MyNiceClass
的Class
對象:
Class cls = Class.forName("com.baeldung.getclassfromstr.MyNiceClass");
assertNotNull(cls);
接下來,讓我們從Class
對象cls
創建一個MyNiceClass
實例。如果我們的 Java 版本早於 9,我們可以使用cls.newInstance()
方法獲取一個實例。但是,**此方法自 Java 9 起已被棄用**。對於較新的 Java 版本,我們可以使用cls.getDeclaredConstructor().newInstance()
從Class
對像中獲取一個新的實例:
MyNiceClass myNiceObject = (MyNiceClass) cls.getDeclaredConstructor().newInstance();
assertNotNull(myNiceObject);
assertEquals("Hi there, I wish you all the best!", myNiceObject.greeting());
當我們運行它時,測試通過了。因此,我們從類名中得到了所需的Class
對象。
值得一提的是,要獲取Class
對象,我們必須向forName()
方法傳遞一個合格的類名,而不是簡單的名稱。例如,我們應該將字符串“com.baeldung.getclassfromstr.MyNiceClass”
傳遞給forName()
方法。否則, forName()
方法會拋出ClassNotFoundException
:
assertThrows(ClassNotFoundException.class, () -> Class.forName("MyNiceClass"));
4. 關於異常處理的幾句話
我們已經了解瞭如何從類名中獲取MyNiceClass
的Class
對象。為簡單起見,我們在測試中省略了異常處理。現在,讓我們看看在使用Class.forName()
和cls.getDeclaredConstructor().newInstance()
方法時應該處理哪些異常。
首先, Class.forName()
拋出ClassNotFoundException.
我們在將MyNiceClass
的簡單名稱傳遞給它時提到了它。 ClassNotFoundException
是一個已檢查異常。因此,我們必須在調用Class.forName()
方法時進行處理。
接下來,讓我們看看cls.getDeclaredConstructor()
和newInstance().
getDeclaredConstructor()
方法拋出**NoSuchMethodException** .
此外, newInstance()
會拋出InstantiationException, IllegalAccessException
、 IllegalArgumentException
和InvocationTargetException
。這五個異常都是檢查異常。所以,如果我們使用這兩種方法,我們需要處理它們。
值得一提的是,我們在本節中討論的所有異常都是ReflectiveOperationException
的子類型。也就是說,如果我們不想單獨處理那些異常,我們可以處理ReflectiveOperationException
,例如:
void someNiceMethod() throws ReflectiveOperationException {
Class cls = Class.forName("com.baeldung.getclassfromstr.MyNiceClass");
MyNiceClass myNiceObject = (MyNiceClass) cls.getDeclaredConstructor().newInstance();
// ...
}
或者,我們可以使用try-catch
塊:
try {
Class cls = Class.forName("com.baeldung.getclassfromstr.MyNiceClass");
MyNiceClass myNiceObject = (MyNiceClass) cls.getDeclaredConstructor().newInstance();
// ...
} catch (ReflectiveOperationException exception) {
// handle the exception
}
5.結論
在這篇簡短的文章中,我們學習了使用Class.forName()
方法從給定的類名字符串中獲取Class
對象。我們應該注意,我們應該將限定名稱傳遞給Class.forName()
方法。
與往常一樣,本文中使用的所有代碼示例都可以在 GitHub 上找到。