Issues with generic type detection of SAM types implemented using lambdas

Oliver Gierke ogierke at pivotal.io
Thu Jan 11 15:34:26 UTC 2018


Again, I think we're discussing different things here. You refer to the fact that from an instance of a generic class, without creating an anonymous subtype, there's no way to find out about the generic type they've been bound to. That's fine and - I guess - common knowledge amongst Java developers.

I am looking a different case and thus a different problem: Lambdas have been advertised as a direct alternative to anonymous classes (see [0], esp. section 12), and that's the reason IDEs unconditionally recommend to convert the latter into the former. However, for a given generic interface, reflecting over the declared generics in the Lambda variant behaves fundamentally different compared to an anonymous implementation.

So I am pretty passionless on whether that's "trying to be clever" or "bad". I was merely pointing out an inconsistency.

Cheers,
Ollie

[0] http://cr.openjdk.java.net/~briangoetz/lambda/lambda-state-final.html

> Am 11.01.2018 um 15:20 schrieb David Lloyd <david.lloyd at redhat.com>:
> 
> On Thu, Jan 11, 2018 at 8:03 AM, Oliver Gierke <ogierke at pivotal.io> wrote:
>>> Am 11.01.2018 um 14:56 schrieb David Lloyd <david.lloyd at redhat.com>:
>>> 
>>> On Thu, Jan 11, 2018 at 3:10 AM, Oliver Gierke <ogierke at pivotal.io> wrote:
>>>> Lambda based implementations of SAM types currently don't support inspecting the type for generic type parameters. This can cause unexpected surprise...
>>> 
>>> Here's a non-lambda example that demonstrates that inspecting *any*
>>> class for generic type parameters is fragile and not a good idea:
>>> 
>>> public final class Hasher<T> implements ToIntFunction<T> {
>>>   int applyAsInt(T value) { return value.hashCode(); }
>>> }
>>> 
>>> Oops, now all my concrete implementations have generic parameters.
>> 
>> I'm afraid I can't follow.
> 
> Your example code which prints the actual type arguments will fail
> because there is no actual type argument declared on the generic
> *type*, only the *instance*.  If you create an API which relies on
> getting actual types off of an object instance's class, you've made a
> usability mistake.
> 
>>> Telling users they cannot have generic parameters on their
>>> implementation classes is poor API design.
>> 
>> Who is actually doing that?
> 
> "I just wanted to point out that an ordinary user -- in general client
> code that uses APIs with SAM types -- *has to implicitly know* whether
> *any code* (potentially Java 6 based) downstream might attempt
> generics resolution before she can decide whether to use a Lambda with
> this SAM type."
> 
> Anyone who wrote one of these APIs is actually doing that.  It has
> nothing to do with lambdas, and everything to do with APIs relying on
> the assumption that implementation classes will have actual values for
> every type parameter that it may inherit.  This assumption is flawed
> because it's completely normal for a user to have a single function
> implementation that works for many types; this is a solid
> memory-conserving technique.  The only thing broken by this are
> "clever" APIs that require usage of getActualTypeArguments() to get
> necessary information from the user.
> 
> --
> - DML

-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 833 bytes
Desc: Message signed with OpenPGP
URL: <http://mail.openjdk.java.net/pipermail/compiler-dev/attachments/20180111/8e51d49d/signature.asc>


More information about the compiler-dev mailing list