SAM resolution

Brian Goetz brian.goetz at oracle.com
Tue Nov 23 11:01:11 PST 2010


If I have:

   interface Mapper<T, U> { U map(T t); }
   interface IntMapper<T> { int map(T t); }

and

class Stream<T> {
   <U> Stream<U> map(Mapper<T, U> mapper);
   IntStream map(IntMapper<T> mapper);
}

and client code

   stream.map(#{ f -> f.someIntField });

I get this error:

reference to map is ambiguous, both method <U>map(Mapper<T,U>) in Stream and 
method map(IntMapper<T>) in Stream match
         stream.map(#{ f -> f.a });
               ^
   where U,T are type-variables:
     U extends Object declared in method <U>map(Mapper<T,U>)
     T extends Object declared in interface Stream

Now, there are clearly two SAM types that are applicable here, so I understand 
the warning.  But the warning seems "surprising" in a sense; in method 
resolution, we "prefer" the match that doesn't require boxing to the one that 
does.  So if we have overloaded
   m(Integer x)
and
   m(int x)

and call m(3), we don't get an ambiguity error.

It is likely to be a common case where people will define "specialized" 
primitive versions of methods along with generic ones.






More information about the lambda-dev mailing list