请解释一下为什么如果我在方法test()中使用原始类型A,我的类型列表上的get()方法返回一个Object而不是B。:
public class test
{
public class B{}
public class C{}
public class A<T extends C>
{
private List<B> aBList;
public List<B> mGetBList()
{
return aBList;
}
}
public test(A pA) // Use of raw type - this is bad, I know!
{
B lB = pA.mGetBList().get(0); // Compile error: Type mismatch:
// cannot convert from Object to test.B
}
}
如果我宣布
public test(A<?> pA)
get()方法按预期返回B.
答案 0 :(得分:2)
“医生,当我这个时会很痛。”
避免像瘟疫这样的原始类型。
答案 1 :(得分:1)
+1有趣的测试用例。
看起来擦除会删除所有内容,所以在这种情况下,你最终会删除。
public List mGetBList()
并且List
的删除将导致public Object get( int )
,当然,这不能分配给B
。
如果方法签名中不需要原始类型,请使用您提供的通用表单,否则将对象强制转换为B
B lB = (B) pA.mGetBList().get(0);
答案 2 :(得分:0)
在方法测试中对参数pa进行decalare时,不包含任何参数(包括通配符)。因此,列表保存在包含对象列表的变量中,因此当您尝试从列表中提取元素时,您将获得一个对象,因此您必须将其强制转换为所需的类型,在本例中为B. / p>
使用通配符时,会告诉编译器不将列表提升为包含保存Object的列表的varibale。它被告知列表中的内容属于“未知类型”,并且要保持独立。然后由程序员决定在提取元素时将其分配给合适的varibale,而不使用强制转换。
答案 3 :(得分:0)
我一直在做一些围绕ang的挖掘发现了这一点。
http://java.sun.com/docs/books/tutorial/extra/generics/legacy.html
基本上,擦除删除(或删除)所有泛型类型信息。抛出尖括号之间的所有类型信息,因此,例如,像List这样的参数化类型被转换为List。 类型变量的所有剩余用法都被类型变量的上限(通常是Object)替换。
如果他们的意思是&lt; T扩展C&gt;,C将是上限,然后因为只有B是aBlist的类型varibable,那么它的上限将是Object。
Anway希望这会有所帮助(请不要再把我标记下来了。)