[英]Java not allowed to call recursive method with generic type?
public class ResourceAssembler<T extends BasedEntity> {
public Resource<T> toResource(T entity) {
ExtendsBasedEntity e = getExtendsBasedEntity();
toResource(e); //<----compile error
//some other code
}
}
public class ExtendsBasedEntity extends BasedEntity{}
但是,如果您從外部調用它,那很好
//some other class
new ResourceAssembler<ExtendsBasedEntity>().toResource(new ExtendsBasedEntity())
為什么?
Error:(28, 25) java: incompatible types: spring.BasedEntity cannot be converted to T
T
可能不是ExtendsBasedEntity
,而是BaseEntity
的其他一些子類型,因此會出現編譯錯誤。
“解決”問題的一種方法是使用類型標記
public class ResourceAssembler<T extends BasedEntity> {
private final Class<T> type;
public ResourceAssembler(Class<T> type) {
this.type = type;
}
public Resource<T> toResource(T entity) {
toResource(type.newInstance());
//some other code
}
}
假設這對你有用。
讓我們創建兩個擴展BasedEntity
的類並將它們命名為EBE1
和EBE2
。
現在,您使用EBE1
作為類型參數創建ResourceAssembly
object。 但是假設在toResource
方法的實現中,您執行了類似return toResource(new EBE2());
.
所以toResource()
的返回類型變成了Resource<EBE2>
但這是錯誤的,因為根據結構你應該返回Resource<EBE1>
。 這就是編譯時錯誤的原因。 Java 的類型安全本能開始發揮作用。
如果您想為toResource
方法返回一個泛型,那么您要么必須按原樣傳遞entity
object,要么將其更改為您正在初始化它的具體類型而不使用泛型(盡管我不知道為什么有人會使用第二個選項,但它是使其“編譯”的“解決方案”)。
此外,在您聲明它時在外面。 您沒有為ResourceAssembly
指定類型參數,因此它是原始參數。 嘗試使用類型參數來完成。 你也會有紅色的波浪線。
這是一個例子:
static class Resource<T> {
}
static class BasedEntity {
}
static class ExtendsBasedEntity1 extends BasedEntity {
}
static class ExtendsBasedEntity2 extends BasedEntity {
}
static public class ResourceAssembler<T extends BasedEntity> {
public Resource<T> toResource(T entity) {
return toResource(new ExtendsBasedEntity1()); //<----compile error
}
}
public static void main(String[] args) {
new ResourceAssembler<ExtendsBasedEntity1>().toResource(new ExtendsBasedEntity1()); // <---- No errors or warnings. This is valid and legal
new ResourceAssembler<ExtendsBasedEntity2>().toResource(new ExtendsBasedEntity1()); // <----- red squiggly lines here
new ResourceAssembler().toResource(new ExtendsBasedEntity2()); // <--compiler warning about raw types but no error
}
如果您無論如何需要使其按您希望的方式工作,那么不要返回Resource<T>
,而是返回Resource<ExtendsBasedEntity>
因為您在泛型方法中遞歸並且看起來您需要一個具體類型的 object 到 go作為遞歸調用的參數。 所以這樣做是有道理的。
或者,go 使用@Bohemian的方法,並確保在您使用的類型的 class 聲明中,有一個無參數構造函數,否則您將擁有InstantiationException
。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.