1 回答

TA貢獻(xiàn)1777條經(jīng)驗(yàn) 獲得超10個贊
這個例子讓我想起了早期,當(dāng)我在“Effective java”一書中閱讀有關(guān)泛型的內(nèi)容時......
首先,這是java泛型的黃金法則:不要混合數(shù)組和泛型,因?yàn)槟阌泻芎玫臋C(jī)會生成不安全的代碼。您的代碼將泛型(例如 T、T extends Card)與數(shù)組(例如 T [] 卡)混合在一起。然后,您在運(yùn)行時得到不安全的代碼。
這是一種安全的方法(首選列表而不是數(shù)組):
class Deck <T extends Card> {
private List<T> cards;
public Deck () {
cards = new ArrayList()<>;
}
}
現(xiàn)在,要回答你的問題,你應(yīng)該首先回到 java 的一些基礎(chǔ)知識:
1- 數(shù)組是共變結(jié)構(gòu)
2-泛型是不變的結(jié)構(gòu)
3-元素類型在數(shù)組中具體化(reification)
4- 參數(shù)類型在通用中被擦除(類型擦除)
不用擔(dān)心,先把可怕的概念放在一邊,看看你的例子發(fā)生了什么:
形式類型 T 在運(yùn)行時被刪除。
這意味著它在字節(jié)碼中被完全刪除。
在第一個示例中,T 只是被替換為 Object,因?yàn)樗亲罱咏念悾ň屠^承而言),所以,
cards = (T []) new Object[52]
被翻譯成
cards = (Object []) new Object[52];
這是安全的。
在第二個示例中, T 綁定到 Card 并且它變成 ,因此,是最接近它的類(就繼承而言),因此,
cards = (T []) new Object[52]
被翻譯成
cards = (Card []) new Object[52];
由于 Object 不是 Card 的子類型,因此您遇到了運(yùn)行時強(qiáng)制轉(zhuǎn)換異常。
添加回答
舉報