Java Reference
In-Depth Information
Heap pollution occurs at (1) because a component in the
stringLists
array that should
refer to a
List<String>
now refers to a
List<Integer>
. There is no way to detect this pol-
lution in the presence of both a universal supertype (
Object[]
) and a non-reifiable type
(the declared type of the formal parameter,
List<String>[]
). No unchecked warning is
justified at (1); nevertheless, at run time, a
ClassCastException
will occur at (2).
A compile-time unchecked warning will be given at any invocation of the method
above because an invocation is considered by the Java programming language's
static type system to create an array whose element type,
List<String>
, is non-reifiable
variable arity parameter, then the programmer could use the
SafeVarargs
annotation to
silence warnings at invocations (§
9.6.3.7
). Since the body of the method as written
above causes heap pollution, it would be completely inappropriate to use the annota-
tion to disable warnings for callers.
Finally, note that the
stringLists
array could be aliased through variables of types other
than
Object[]
, and heap pollution could still occur. For example, the type of the
array
variable could be
java.util.Collection[]
- a raw element type - and the body of the method
above would compile without warnings or errors and still cause heap pollution. And if
the Java SE platform defined, say,
Sequence
as a non-generic supertype of
List<T>
, then
using
Sequence
as the type of
array
would also cause heap pollution.
The variable will always refer to an object that is an instance of a class that represents the
parameterized type.
The value of
ls
in the example above is always an instance of a class that provides a
representation of a
List
.
Assignment from an expression of a raw type to a variable of a parameterized type
should only be used when combining legacy code which does not make use of para-
meterized types with more modern code that does.
If no operation that requires a compile-time unchecked warning to be issued takes
place, and no unsafe aliasing occurs of array variables with non-reifiable element
types, then heap pollution cannot occur. Note that this does not imply that heap pollu-
tion only occurs if a compile-time unchecked warning actually occurred. It is possible
to run a program where some of the binaries were produced by a compiler for an older
version of the Java programming language, or from sources that explicitly suppressed
unchecked warnings. This practice is unhealthy at best.
Conversely, it is possible that despite executing code that could (and perhaps did)
give rise to a compile-time unchecked warning, no heap pollution takes place. Indeed,