这两种方法有什么区别?
public <T extends Serializable, Y extends List<T>> void foo(Y y, T t);
和
public void foo(Serializable ser, List<Serializable> list);
答案 0 :(得分:5)
可以使用List<String>
(例如)作为参数调用第一个。第二个不能,因为List<String>
不是List<Serializable>
。
可以使用Integer
作为第一个参数调用第二个参数,并使用List<Serializable>
作为第二个参数。但是,如果另一个参数是List<Integer>
,则第一个只接受Integer
作为参数。
答案 1 :(得分:3)
public <T extends Serializable, Y extends List<T>> void foo(Y y, T t);
此函数中的泛型强制您指定完全类型T
,并且两个参数中的完全必须相同。不允许使用T
的子类,它必须是 类型。否则编译器将不允许。
public void foo(Serializable ser, List<Serializable> list);
在这个非泛型函数中,参数类型之间没有关系,除了它们都是Serializable
。这允许ser
任何 类型Serializable
,list
中的元素 任意 Serializable
的类型。它们可能是同一类型,也可能不是。它与编译器无关。
可能正在阅读此内容的任何新手的更多信息:
泛型仅存在于源代码中。编译代码后它们不存在。这称为“类型擦除”:
https://www.google.com/search?q=type+erasure+java
这种擦除已经完成,因此预泛化代码可以与泛型代码互操作。因此,在引入泛型之前存在的代码不会 进行更改。鼓励新代码始终使用泛型。