Inner class type parameter bound by enclosing class type variable
Is there any way to use a type variable declared by an enclosing class as a bound on a type variable declared in an inner class?
class Test<E> {
class Inner<T extends开发者_JAVA百科 E> {}
<T extends E> void doStuff(T arg) {}
public static void main(String[] args) {
new Test<Number>().doStuff(new Integer(0)); // works fine, as expected
new Test<Number>().new Inner<Integer>(); // won't compile
}
}
javac gives this error:
Test.java:6: type parameter java.lang.Integer is not within its bound
new Test<Number>().new Inner<Integer>();
^
I can't find any combination of types that will satisfy the compiler. What's the difference between the type parameter T
as declared by Inner
versus doStuff
? Why does one work and the other doesn't?
I'm not looking for an alternative, I just want to gain a better understanding of how the language works.
http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=6557954
Bug ID: 6557954
Votes 2
Synopsis Inner class type parameters doesn't get substituted when checking type well-formedness
Category java:compiler
Release Fixed 7(b40)
State 10-Fix Delivered, bug
Priority: 5-Very Low
Submit Date 16-MAY-2007
Posted Date : 2008-07-02 16:22:46.0
Description
The compiler fails to accept this program:
class Foo<T> {
class Bar<U extends T> {}
Foo<Number>.Bar<Integer> f;
}
Evaluation
This is a problem in Check.java as when checking for bound-conformance actual type parameters are subsituted only in topmost type-variable's bound. In this case we have that Foo.Bar is to be checked against the actual type-parameters T=Number, U=Integer
So it should be the case that:
Number <: Object
Integer <: [Number/T]T = Number
unfortunately, javac misses the second substitution so that the check becomes:
Integer <: T
which is wrong and cause the error.
Edit:
On my system, the code in the question compiles without error with Java 7 javac
:
C:\workspace\Sandbox\src>"%JAVA_HOME%\bin\javac.exe" -version
javac 1.7.0-ea
But it fails with the error indicated in the question for Java 6 javac
:
C:\workspace\Sandbox\src>"%JAVA_HOME%\bin\javac.exe" -version
javac 1.6.0_17
精彩评论