Java泛型 - 桥接方法

时间:2011-07-02 14:26:13

标签: java generics

当谈到bridge方法时,我知道java编译器会在需要时添加它们,以便子类可以正确地完成覆盖(在阅读了mughal和angelikalanger网站的SCJP之后)。但这有点令人困惑,如下所示:

在删除之前:

class x <T> {  
   void set(T t){}  
}

class y <E> extends x {  
   void set(E e) {} // name clash here  
}

class z<E> extends x {  
   void set(Object y) {} // no name clash here  
}

class z1<E> extends x<T> {  
   void set(Object y) {} // name clash here  
}
擦除后

class x {  
   void set (Object t) {}  
}

我理解y类的名称冲突,但为什么z类没有名称冲突? 类z1也有名称冲突?令人费解的

2 个答案:

答案 0 :(得分:2)

class y <E> extends x {  
   void set(E e) {} // name clash here  
}

这里发生名称冲突,因为E不是T的子类。所以你不能用这种方式覆盖set方法。请参阅z1的解释以便更好地理解。 要使y级工作,你必须

class y <E> extends x<E> {  
   void set(E e) {}  
}

下一步:

class z<E> extends x {  
   void set(Object y) {} // no name clash here  
}

这里没有名称冲突,因为在类X中,set方法被解释为

void set(java.lang.Object) 

并且在类z中,set的参数也是java.lang.Object.so no clash。

下一步:

class z1<E> extends x<T> {  
   void set(Object y) {} // name clash here  
}

此处发生名称冲突,因为您必须具有设置为x提供的任何类型参数的参数。在这里,您传递给x类型参数T,但您将set方法的参数作为java.lang.Object。因此命名冲突。

要使z工作,你必须:

class z1<E> extends x<Object> {  
       void set(Object y) {}  
}

答案 1 :(得分:1)

正如你所说,在擦除之后set方法接受一个Object。在删除z

之后,x扩展了非泛型