18

我有

public class First<T> {}

public class Second<T extends SomeConcreteClass> extends First<T> {}

public class Third<T> extends Second<T> {} //Compile-time error

我收到编译时错误

Type argument T is not with bounds of type-variable T.

当我构造 aThird时,我希望能够将泛型参数作为SomeConcreteClass(或其派生类),并且如果我提供的类型不是SomeConcreteClass的继承层次结构的一部分,则会引发运行时错误.

我认为Second' 的声明中的规范只会向下传播,即它应该隐含在 . 的声明(和任何实例化)中Third

错误是怎么回事?

4

4 回答 4

22

所有你需要的是

public class Third<T extends SomeConcreteClass> extends Second<T>

您只需要重新指定界限。它不会像你想象的那样传播。

(我不肯定这个原因,但我有一些猜测——如果是这样Third<T> extends Second<Foo<T>>呢?适当的界限T并不明显,即使有一个。所以相反,它只是不会自动传播;你必须指定它。)

于 2012-07-19T12:34:29.987 回答
2

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

public class Third<T> extends Second<T> {}

有了这个:

public class Third extends Second<SomeConcreteClass> {}

要在构造函数中使用 T 或在代码中使用 T 类型的成员字段,例如 T 类型的成员字段,则可以这样做:

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>

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

于 2015-05-05T14:45:46.517 回答
1

您有边界限制的向下传播。

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

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> {} 

请注意,现在很明显您不能拥有

public class Third<T> extends Second<T> {} 

由于您缺少T2. Second<V,T2>当你使用一个具体的类时,这个限制就变得隐含了。

于 2012-07-19T13:10:52.607 回答
0

public class Third<T> extends Second<T> {}

这是一个绑定不匹配。当您刚刚指定 second 的类型为 T 而不是扩展 SomeConcreteClass 时,您不能使用泛型 T 扩展 Second。当你扩展 Second 时,你需要使用 SomeConcreteClass 范围内的东西。

public class Third<T> extends Second<ClassThatExtendsSomeConcreteClass> {}

要不就

public class Third<T> extends Second<SomeConcreteClass> {}

于 2012-07-19T12:37:45.197 回答