3

详细解释以下两个版本的 Java 泛型类之间的区别(如果有)?

class C<T>{
    T x;
    void foo(T y)  { … }
}

class C<T>{
    T x;
    <T> void foo(T y)  { … }
}

还有另一个问题:在 foo() 的主体中可以写什么,替换将导致 Java 编译器接受 C 的第一个版本但拒绝 C 的第二个版本的“...”。

我很困惑。

4

2 回答 2

10
class C<T>{
    T x;
    <T> void foo(T y)  { … }
}

是一种令人困惑的写作方式

class C<T>{
    T x;
    <S> void foo(S y)  { … }
}

至于什么会拒绝第二个版本,例如:

class C<T>{
    T x;
    <T> void foo(T y)  { x = y; }
}

将失败,因为如果您将其重写为

class C<T>{
    T x;
    <S> void foo(S y)  { x = y; }
}

您可以立即看到您缺少演员表(确切的编译器错误是“不兼容的类型”)。

于 2012-05-12T22:13:02.610 回答
2

在第一个示例中,T方法中的类型变量foo表示与类定义中声明的类型完全相同C<T>

第二个例子是一个陷阱,因为T方法声明中的 是完全不同的类型,与类的类型参数无关,只是碰巧同名T。这与局部变量隐藏同名字段的情况类似。

对于这种情况,Eclipse 会发出一个很好的编译器警告(如果在设置中打开了此警告,则不确定它是否默认打开):

类型参数 T 隐藏了类型 T

于 2012-05-12T22:20:47.600 回答