Hi,
I tested all 6 combinations of Functions that a simple sanity-check StackWalker
can call:
Function<? super Stream<? extends StackFrame>, [any]>
Function<? super Stream<? super StackFrame>, [any]>
Function<? super Stream<StackFrame>, [any]>
Function<Stream<? extends StackFrame>, [any]>
Function<Stream<? super StackFrame>, [any]>
Function<Stream<StackFrame>, [any]>
Unfortunately there doesn’t appear to be any candidate for the walk-method that
doesn’t have at least one counterexample which is well-typed and doesn’t
compile. Remi’s Function<Stream<Object>, Void> is one example which doesn’t
compile against any of the six.
static Function<? extends Stream<?>, Long> meekCounter() {
return Stream::count;
}
That one is another such example, a bit surprisingly.
So this means you can’t support all clients at the same time.
Sent from Mail for Windows 10
From: Mandy Chung
Sent: Thursday, November 5, 2015 22:49
To: Remi Forax
Cc: [email protected]
Subject: Re: Proposed API for JEP 259: Stack-Walking API
> On Nov 4, 2015, at 5:00 AM, Remi Forax <[email protected]> wrote:
>
>>
>> Good point. Damn, i don’t like wildcards :-)
>>
>> The following works fine:
>>
>> static <T> Function<Stream<T>, Long> counter() {
>> return Stream::count;
>> }
>>
>> But there could also cases where one is stuck using a wildcard:
>>
>> Function<Stream<?>, Long> f = Stream::count;
>
>
> Wildcards are not that complex, but because they are use-side annotations,
> it's really easy to forget them, and IDEs do not help here :(
>
> I really hope that the JEP about declaration site variance [1] will be
> implemented at the beginning of jdk 10, it will remove the need of wildcards
> for functional interfaces.
>
Remi, Paul,
The current StackWalker::walk method:
<T> T walk(Function<Stream<StackFrame>, T> function)
This would mean that the StackWalker API is intended to work with a function
taking Stream<StackFrame> but not Stream<?>.
Changing to
<T> T walk(Function<? super Stream<StackFrame>, ? extends T> function)
will allow use of some existing functions taking Stream<?>. I don’t object
changing it to use wildcard.
However, the StackWalker API is specific for reading StackFrame and I would
expect it’s reasonable if it doesn’t work with a function taking Stream<?> as
the useful functions such as Stream::count,
Stream::collect(Collectors.toList(…)) can be used.
Just want to double confirm the advice which way to go.
Mandy