Collectors update
Remi Forax
forax at univ-mlv.fr
Tue Jan 29 16:34:42 PST 2013
On 01/30/2013 12:22 AM, Brian Goetz wrote:
>>> 4. Rejigger Partition to return an array again, with an explicit
>>> lambda (which will likely be an array ctor ref) to make the array.
>>> Eliminated the silly Partition class.
>>
>> Please don't do that, it's pure evil.
>
> The silly Partition class was also evil. We're in the "lesser of
> evils" business here.
>
>> public static<T> Collector<T, Collection<T>[]>
>> partitioningBy(Predicate<T> predicate, IntFunction<Collection<T>[]>
>> arraySupplier) {
>>
>> in order to call this method users have to send a lambda that creates an
>> array of parametrized type something which will be unsafe (the only way
>> to get type safety is to create a class that inherits from Collection
>> and to provide a type argument something like class Foo extends
>> ArrayList<String> {}) so while the code of the library is typesafe, no
>> user code will never be typesafe.
>
> Yes, let's have this discussion. The above is true, but is this
> really a problem?
yes, it is.
Arrays of parametrized type are unsafe to create unless you can subclass
the component type.
By example,
enum Foo { }
Enum<Foo>[] array = Foo.values();
is safe. but
Enum<Foo>[] array = new Enum<>[2];
is not safe, and should even not compile because you can not use the
diamond syntax on an array.
> The array is simply a box for carrying the result back. The typical
> use case will be:
> - call partition
> - scoop out the two collections / reductions / whatever
> - throw away the box
>
> So the box is intended to be a short-lived container (essentially a
> workaround for the lack of tuples.)
if you want a tupe, just create a class Tuple (with a private constructor),
the other solution is to not include partioningBy in jdk8 and wait 9.
Now, why it's unsafe, let say we have:
Collection<String>[] csa = stream.collect(Collectors.partioningBy( ...));
one can write
Object[] array = csa;
array[0] = Arrays.asList(1);
and later
String s = csa[0].get(); // ClassCastException
> This is not the same case as Stream.toArray.
no, it's not. toArray can be used in a safely manner or not.
partionningBy is (almost) never safe.
>
>> and BTW, the IntFunction will be always called with 2 as argument.
>
> Yes. Is that bad?
>
why not using a Supplier ?
Rémi
More information about the lambda-libs-spec-observers
mailing list