Community
Participate
Working Groups
I200408241200 public class Main { public static void main(String[] args) { new C<Double,Integer>().foo(new Integer(1)); //1 new C<Double,Integer>().foo(new Double(2)); //2 new C<Number,Number>().foo(new Integer(3)); //3 } } class B <Tb> { void foo(Tb b) { System.out.println("B: "+b); } } class C <Tb, Tc> extends B<Tb> { void foo(Tc c) { System.out.println("C: "+c); } } Running Main produces C: 1, C: 2.0, C: 3. Hovering over foo(..) at //2 shows "void inherit.B<Tb>.foo(Tb b)". The ASTView says that the method binding at line //2 is "B<Double>.foo(Double)". Is this OK since the (erased) C#foo(..) overrides B#foo(..) at run time, but not at compile time? I'm not really sure here - this would be very C++ish ;-( However, I think //3 should raise an "ambiguous method invocation" error, since none of the foo(..) methods is "most specific" in this case. BTW: Sun's javac 1.5.0-beta3-b62 says: reference to foo is ambiguous, both method foo(Tb) in inherit.B<java.lang.Number> and method foo(Tc) in inherit.C<java.lang.Number,java.lang.Number> match new C<Number,Number>().foo(new Integer(3)); //3 ^ ... and after removing the offending third call to foo: name clash: foo(Tc) in inherit.C<Tb,Tc> and foo(Tb) in inherit.B<Tb> have the same erasure, yet neither overrides the other class C <Tb, Tc> extends B<Tb> { ^
We now issue the nameclash issue correctly. Kent - pls double check and add regression test.
We correctly generate the name clash but we don't detect the ambiguous error (yet).
I cannot see why the 2 methods would be ambiguous... the name clash, which we do generate, I can understand but not the ambiguous error. Can anyone create a testcase with only the ambiguous error? I've tried to but have yet to do it.
Change "class C <Tb, Tc>" to "class C <Tb, Tc extends Number>". This new C has methods - foo(Tb), with erasure foo(Object) - foo(Tc), with erasure foo(Number) -> they don't clash any more. Now, with the instantiation new C<Number, Number>(), Tb and Tc become equal at the method invocation //3, and the compiler cannot know which foo is meant. Note that the two foos don't override, since their erasures are different.
thx
Added MethodVerify test043
Verified in I20050330-0500