[英]Get generic type of class at runtime is not working
我有兩個類和一個接口
public class ExcelReader<T> extends Reader<T> implements RowColumnReader<T> {
// private final TypeToken<T> typeToken = new TypeToken<T>(getClass()) {};
// private final Type type = typeToken.getType();
/* public Type getType() {
return type;
}*/
// Useing Guava getting System.out.println(reader.getType()) T as ouput
@Override
public List<T> readFile(String file) {
//my code
}
}
public abstract class Reader<T> {
protected Class<T> clazz;
/*public Reader() {
clazz = (Class<T>) ((ParameterizedType) getClass().getGenericSuperclass()).getActualTypeArguments()[0];
}*/
// Constructor is commented beacuse getting Exception java.lang.ClassCastException: sun.reflect.generics.reflectiveObjects.TypeVariableImpl cannot be cast to java.lang.Class
}
public interface RowColumnReader<T> extends HeaderFields<T>{
public List<T> readFile(String file);
}
public interface HeaderFields<T> {
default List<String> getHeader(Class<T> clazz) throws HeaderNotDefiendException {
//my code
return headerList;
}
}
我已經嘗試了所有可能的方法來獲得泛型類。 我在運行時跟隨了Get泛型類,甚至嘗試了該頁面中給出的所有解決方案。 但仍然沒有運氣。
即使有高瓦
https://stackoverflow.com/a/19775924/2290078得到getType()
的輸出是T不是實際的泛型類
我的測試代碼是
Reader<Test> reader = new ExcelReader<>();
//System.out.println(reader.getType()); ---> output is T
List<Test> list = reader.readFile("Sample.xlsx");
System.out.println(list);
這不僅僅是“我應該使用什么API來在運行時獲取泛型類型?”。 這取決於你想用泛型類型( T
)做什么。
泛型更多的是編譯時檢查功能,可以使用T extends
和T super
強加一些有用的限制。 而已。 這可能是有用的區別<? 超級T>和<? 在Java中擴展T>
如果你想在運行時知道類型T
並使用像switch
這樣的東西來執行條件實現,那么你聲明泛型的類並不是真正的泛型類,因為不同類型的實現不同,因此它沒有得到優雅的支持。
我已經嘗試了所有可能的方法來獲得泛型類。
您在此處找到的這種方式無法檢索通用:
public Reader() {
clazz = (Class<T>) ((ParameterizedType) getClass().getGenericSuperclass()).getActualTypeArguments()[0];
}
因為它靜態檢索在Reader
的直接超類中定義的參數化類型,在本例中是Object
。
在子類構造函數中移動此代碼也不起作用:
public ExcelReader() {
clazz = (Class<T>) ((ParameterizedType) getClass().getGenericSuperclass()).getActualTypeArguments()[0];
}
因為它靜態檢索Reader
類中定義的參數化類型,即T
由於T
沒有任何綁定,您仍然可以將Object
類作為返回的類。
哪種解決方案適用於您的情況?
編譯后會刪除泛型。 所以要注意運行時使用的參數化類型信息是Test
:
Reader<Test> reader = new ExcelReader<>();
你必須在實際代碼中明確地“傳遞”代表泛型的Class
。
為此,在構造函數中添加一個表示泛型類型的Class
參數,並將其存儲在字段中。 現在,您可以在運行時引用該類型。
public class ExcelReader<T> extends Reader<T> implements RowColumnReader<T> {
private Class<T> genericType;
public ExcelReader(Class<T> genericType){
this.genericType = genericType;
}
/*...*/
}
現在,您可以通過以下方式實例化ExcelReader
:
ExcelReader<Test> excelReader = new ExcelReader<>(Test.class);
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.