class Bouncy<T> extends Throwable { } // Error: the generic class Bouncy<T> may not subclass java.lang.Throwable
Why doesn't Java support generic Throwable
s?
I realize that type erasure complicates certain things, but obviously Java gets by with a lot already, so why not push it one more notch and allow generic Throwable
s, with comprehensive compile-time check for potential problems?
I feel like the type erasure argument is rather weak. Currently, we can't do:
void process(List<String> list) { } void process(List<Integer> list) { }
Of course, we get by without it. I'm not asking that we should be able to do catch Bouncy<T1>
and Bouncy<T2>
in the same try
block, but if we use them in disjoint contexts with strict compile-time enforceable rules (which is pretty much the way generics works right now), wouldn't it be workable?
The Java Generics programming is introduced in J2SE 5 to deal with type-safe objects. It makes the code stable by detecting the bugs at compile time. Before generics, we can store any type of objects in the collection, i.e., non-generic. Now generics force the java programmer to store a specific type of objects.
If generic array creation were legal, then compiler generated casts would correct the program at compile time but it can fail at runtime, which violates the core fundamental system of generic types.
Using generics, primitive types can not be passed as type parameters. In the example given below, if we pass int primitive type to box class, then compiler will complain. To mitigate the same, we need to pass the Integer object instead of int primitive type.
“Java Generics are a language feature that allows for definition and use of generic types and methods.” Generic types are instantiated to form parameterized types by providing actual type arguments that replace the formal type parameters. A class like LinkedList<E> is a generic type, that has a type parameter E .
Java Language Specification 8.1.2 Generic Classes and Type Parameters:
This restriction is needed since the catch mechanism of the Java virtual machine works only with non-generic classes.
Personally, I think it's because we can't get any benefits of generics inside a catch
clause. We can't write catch (Bouncy<String> ex)
due to type erasure, but if we write catch (Bouncy ex)
, it would be useless to make it generic.
Short answer: because they took shortcuts, just like they did with erasure.
Long answer: as others already indicated, because of erasure, there is no way to make a difference at runtime between a "catch MyException<String>" and "catch MyException<Integer>".
But that doesn't mean that there is no need for generic exceptions. I want generics to be able to use generic fields! They could have simply allowed generic exceptions, but only allow catching them in the raw state (e.g. "catch MyException").
Granted, this would make generics even more complicated. This is to show just how bad the decision to erase generics was. When will we have a Java version that supports real generics (with RTTI), not the current syntactic sugar?
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With