SAM types and functions

Mark Reinhold mr at sun.com
Thu Dec 10 22:23:43 PST 2009


> Date: Thu, 10 Dec 2009 22:38:03 +0000
> From: alex.blewitt at gmail.com

>> Many existing Java libraries define interfaces which declare just one
>> method or abstract classes which declare just one abstract method (so-
>> called "SAM" types).  A function of appropriate type is converted to
>> an anonymous instance ...
> 
> I'm not sure this is needed in the general case; where it could be
> used is in (say) Comparators. However, having a Collections static
> method (say, Comparable c = Collections.comparable(#int(Object a,
> Object b)) would be sufficient to convert a lambda into a Comparable.

(I suspect you really mean

     <T> Collections.comparable(#int(T,T))

 but that's beside the point.)

> I think the addition of the SAM conversion adds unnecessary complexity
> and shouldn't necessarily be implemented if it causes the detriment of
> the addition of lambdas to the language; after all, many of the
> problems of existing proposals have been due to increased complexity.

I agree that if SAM conversion proves problematic then we should drop it,
at least for now.  I do, however, think we should try to figure out a way
to support it.

> That's not to say I don't see the benefit of doing this; but what
> happens if additional abstract methods are added to a class? That
> sounds like something to generate a lot of headaches in the edge cases.

How often does that happen?

Adding a new abstract method to a class is pretty much the same thing as
adding a new method to an interface.  You're asking for trouble.  Don't
do it.  (Unless you control every class that extends that abstract class,
which is rarely the case.)  Such a modification is "binary compatible"
per the JLS [1], but any code compiled against the new class will fail
miserably if it attempts to invoke the new method upon an instance of a
subclass that was compiled against the old version of the abstract class.

(For that reason we don't do this in the platform, with a (very) small
 number of exceptions (e.g., JDBC) where the number of implementors of
 the interfaces/abstract classes is manageably small.)

If the author of an abstract class decides to add a new abstract method
to that class then any existing class files defining functions that are
converted to instances of that class will continue to work just fine.
It's only newly-compiled clients of the class that may fail, if and when
they attempt to invoke the new method.

In short, I don't think this is any different from the situation we
already have today.  If the author of an abstract class or interface
decides to add a new abstract method then the consequences are their
burden to bear.

- Mark


[1] http://java.sun.com/docs/books/jls/third_edition/html/binaryComp.html


More information about the lambda-dev mailing list