//java architect /
programs contained missing dependencies or referenced old repositories. Our
final selection includes software written
both before and after the introduction
of generics and comprises more than
5 million lines of code.
We customized the Java compiler
that is freely available as part of the
OpenJDK, modifying the type checker
to make arrays invariant. In this way, we
could simply use the compiler to identify
any uses of covariant arrays in our code
corpus, because these uses would be
reported as compile errors.
This required changing the method
isSubtypeUnchecked(Type t, Type s, Warner
warn), which is called by the compiler to
check whether two types are subtypes
(that is, whether or not one type is sub-stitutable for the other). Whenever this
method was called with array types, we
required the types of the two arrays to
be identical:
COMMUNITY
if (t.tag == ARRAY && s.tag ==
ARRAY) {
}
JAVA IN ACTION
As a result, uses of covariant arrays
are reported as a compile error. For
example, the code in Listing 1 returns
the following two errors:
YOUR
LOCAL JAVA
USER GROUP
NEEDS YOU
Find your JUG here
2% 9%
Main.java:5:incompatible types
found: java.lang.String[]
required: &java.lang.Object[]
Object[]=new String[ 10];
Main.java:10:incompatible types
found: java.lang.String[]
required: java.lang.Object[]
return new String[ 10];
ABOUT US
11%
Method call
Constructor call
Assignment
Return statement
78%
Figure 1
16%
User-defined
Library
84%
Figure 2
Results of the Study
We ran the modified Java compiler
over our corpus and discovered 324 uses
of covariant arrays in 9 out of 64 programs. This is a surprisingly low number
considering that our corpus exceeds
5 million lines of code, which equates to
one covariant array use for every 15,000
lines of code. This indicates that covariant arrays are used very infrequently.
Figure 1 shows the contexts in which
covariant use of arrays occurred. The
vast majority of these uses (89 percent)
occurred when a method or constructor
was called with a subtype of the required
array parameter type. For example, if we
called our find(Object item, Object[] arr)
method from above with an argument of
type String[], this would be classified as a
covariant method call.
blog
46
ORACLE.COM/JAVAMAGAZINE /////////////////////////////////////////////// MAY/JUNE 2012