使用泛型参数扩展的多级Java泛型继承

使用泛型参数扩展的多级Java泛型继承,java,generics,Java,Generics,我有 当我构造第三个时,我希望能够将泛型参数指定为SomeConcreteClass(或其派生类),如果我提供的类型不是SomeConcreteClass继承层次结构的一部分,则抛出运行时错误 我认为第二个声明中的规范只会向下传播,即它应该隐含在第三个的声明(以及任何实例化)中 错误是怎么回事?您只需要 Type argument T is not with bounds of type-variable T. 公共类第三次扩展第二次 您只需要重新指定边界。它不像你想象的那样传播 (我不确定

我有


当我构造第三个
时,我希望能够将泛型参数指定为
SomeConcreteClass
(或其派生类),如果我提供的类型不是
SomeConcreteClass
继承层次结构的一部分,则抛出运行时错误

我认为
第二个
声明中的规范只会向下传播,即它应该隐含在
第三个
的声明(以及任何实例化)中

错误是怎么回事?

您只需要

Type argument T is not with bounds of type-variable T.
公共类第三次扩展第二次
您只需要重新指定边界。它不像你想象的那样传播

(我不确定原因,但我有一些猜测——如果是
Third extends Second
,怎么办?
T
的适当界限并不明显,如果有。因此,它只是不会自动传播;您必须指定它。)

公共类Third extends Second

这是一个界限不匹配。当您刚刚指定Second的类型为t而不是扩展SomeConcreteClass时,不能使用泛型t扩展Second。当您扩展Second时,您需要使用SomeConcreteClass范围内的内容来扩展Second

公共类第三次扩展第二次{}

或者只是


公共类第三次扩展第二次{}

边界限制向下传播

如果您将代码放在上面的通用术语中,您将清楚地看到受限声明。此外,任何进一步的继承也需要保留或进一步缩小这一限制。例如:

public class Third<T extends SomeConcreteClass> extends Second<T>
公共类优先{}
公共类第二次扩展第一次{}
公共类第三次扩展第二次{}
请注意,现在很清楚,您不能

public class First<T> {}

public class Second<U, T1 extends U> extends First<T1> {}

public class Third<V, T2 extends V> extends Second<V,T2> {} 
公共类第三次扩展第二次{}
由于缺少所需的
T2
第二个
的类型信息。

当您使用一个具体的类时,这个限制就隐式了。

在我们的例子中,您可能可以替换它:

public class Third<T> extends Second<T> {} 
公共类第三次扩展第二次{}
为此:

public class Third<T> extends Second<T> {}
公共类第三次扩展第二次{}
要在构造函数中使用T,或者在代码中使用T,例如类型为T的成员字段,则可以执行以下操作:

public class Third extends Second<SomeConcreteClass> {}
VB2扩展了VB1
...
公共VB2(Frag2 frag){。。。
VB1扩展了公共vb
...
公共V1(T frag){…///注意T
CommonV扩展了BaseVB
...
公共公共VB(T控制器){。。。
BaseVB

这是可行的。重要的是,具体类上的泛型必须指定实际的具体片段类,以便VB类中的其他代码访问其方法。

啊,因此没有向下传播。这很不幸。感谢您的响应。“如果我提供了一个不是部分的类型,则会抛出一个运行时错误”。我认为您无法获得该错误。“提供类型”仅在编译时发生(然后被删除)。如果禁用该错误(通过不“提供”任何类型),您可能会在某个时候得到ClassCastException,但稍后,在构建第三个实例时就不会了
public class Third extends Second<SomeConcreteClass> {}
VB2 extends VB1<Frag2>
...
public VB2(Frag2 frag){...

VB1<T extends Frag1> extends CommonVB<T>
...
public V1(T frag){... /// notice the T

CommonV<T extends CommonFragBase> extends BaseVB<T>
...
public CommonVB(T controller) {...

BaseVB<T extends CommonFragBase>