[英]java generic method warning “Unchecked cast”
我相信這就是警告的原因:Java允許向下轉換,即將類型X的對象轉換為X的子類。但是,這需要在運行時進行檢查。 例如:
Object x1 = <... something that returns an object that may be a String ...>;
String x2 = (String)x1;
演員將嘗試將x1
視為String
。 但是x1
可以是任何Object
。 它可能是也可能不是String
。 只有當x1
實際上是一個String
; 否則你在運行時得到一個ClassCastException
。
代碼中的問題是T
是View
的子類,這意味着強制轉換通常會導致在運行時執行相同類型的檢查。 但是,由於類型擦除,程序在代碼中此時實際上並沒有關於T
類的信息,這意味着它無法執行檢查。 因此,您將使用未經檢查的操作收到有關該程序的警告。 程序無法保證,當此方法返回時,返回的對象實際上將是T
類的實例。
我嘗試了一些測試用例,發現檢查通常發生在調用泛型方法的語句中。 假設View2
擴展了View
,並且您希望以返回View2
的方式使用find
。 然后:
View2 v = YourClass.<View2>find(x, id);
如果findViewById
找到的對象實際上不是View2
,那么你將得到一個ClassCastException
。 但:
View v = YourClass.<View2>find(x, id);
假設findViewById
返回其他一些視圖。 基於我的測試,即使type參數是View2
,也不會拋出異常; 因為這被分配到一個View
,如果結果是其他視圖,它將正常工作,不會檢查View2
。
String s = YourClass.<View2>find(x, id).toString();
假設findViewById
返回其他一些視圖。 當我嘗試這個時,我認為它不會拋出異常,因為另一個視圖也會有toString()
(就像所有的Object
一樣)。 但這確實拋出了ClassCastException
。
我不知道是否有一個很好的方法來解決它。 一種可能性是添加第三個參數來find
以表示T
的類,並使用其cast
方法:
public static <T extends View> T find(View view, int id, Class<T> theClass) {
return theClass.cast(view.findViewById(id));
}
View v = YourClass.find(x, id, View2.class);
這有效 - 如果findViewById
返回錯誤的類,它會從cast()
方法拋出異常。 但是,為每次使用添加第三個參數可能不太吸引人,即使它可能允許您從調用中消除顯式泛型類型參數。
我認為這是一個可以忽略警告的情況,並使用@SuppressWarnings("unchecked")
來停止警告顯示,如果你可能有時程序可能會繼續而不是拋出異常當findViewById
返回錯誤的視圖時。
( 免責聲明:我的測試是使用Java 8進行的。我沒有使用任何在Java 7中無效的東西。但是如果Android仍然沒有完全實現Java 7,我寫的一些內容可能是錯誤的。)
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.