Chúng tôi hiện đang trong quá trình di chuyển một ứng dụng từ Java 7 sang Java 8. Sau khi khắc phục một số vấn đề biên dịch, tôi tình cờ gặp một vấn đề tương tự như câu hỏi sau: ClassCast Error: Java 7 vs Java 8.Làm thế nào để phát hiện các cuộc gọi phương thức không rõ ràng có thể gây ra một ClassCastException trong Java 8?
Nói tóm lại, đây là một mẫu mã cho thấy vấn đề này:
public class Test {
public static void main(String[] args) {
System.out.println(String.valueOf(getVal("xxx"))); // 7: prints the result, 8: Exception
}
@SuppressWarnings("unchecked")
public static <T> T getVal(String param) {
// do some computation based on param...
return (T) result; // actual return type only depends on param so the caller knows what to expect
}
}
Ý tưởng là chúng tôi sẽ đẩy mà người gọi biết kiểu mong đợi, và điều này sẽ tránh anh ta chuyển kiểu tường minh (tôi đừng nói đây là một ý hay ...). Trong rất nhiều trường hợp, người gọi chỉ mong đợi một Object
vì vậy không có diễn viên tiềm ẩn nào cả.
Như đã nêu trong câu hỏi trên, ví dụ String.valueOf
hoạt động tốt trong Java 7 vì không có suy luận kiểu, do đó, giả sử Object
. Bây giờ trong Java 8, trình biên dịch chọn loại cụ thể nhất (ở đây char[]
), gây ra một ClastCastException
khi chạy.
Vấn đề là chúng tôi có khoảng 350 cuộc gọi của phương thức getVal
này. Có cách nào để phát hiện các cuộc gọi phương thức quá tải sẽ khác nhau giữa Java 7 và Java 8 không? I.E. phát hiện khi trình biên dịch Java 8 sẽ chọn một phương thức khác với trình biên dịch Java 7.
Chúng tôi đã có một phương pháp tương tự cũng được gọi trong hàng trăm địa điểm. Tôi đã thay thế nó bằng cách giới thiệu tham số 'Class clazz' bổ sung. Bằng cách này bạn có thể xử lý lỗi rõ ràng: trả về null hoặc ném một số ngoại lệ cụ thể hơn. Tôi chỉ làm điều này bằng tay chi tiêu như nửa giờ. Tôi khuyên bạn nên làm như vậy. Tôi không biết làm thế nào để tự động hóa nó, do đó điều này không đủ điều kiện như là một câu trả lời cho câu hỏi của bạn. –
Có một câu trả lời đơn giản: * không chặn cảnh báo “không được kiểm tra” *. Họ đã nói với bạn rằng mã của bạn là sai. Nếu bạn muốn sửa mã của mình ngay bây giờ đã quá muộn, chỉ cần tìm kiếm các lần xuất hiện của '@SuppressWarnings (" không được kiểm tra ")'… – Holger
@Holger Bạn có thể nói điều đó với đồng nghiệp của tôi khi thực hiện điều này trong năm 2011 không? ;-) Tôi đã biết nó là một ý tưởng tồi ở nơi đầu tiên (mặc dù không phải là xấu như bây giờ trong Java 8). Ngoài ra, không có '@ SuppressWarnings' trên phương thức gọi chính nó, nó chỉ trong khai báo' getVal'. Việc xóa chú thích này ở đây sẽ không hiển thị bất kỳ tập quán nào có vấn đề. –