I'm doing a series of streaming operations to flatten what's effectively a 2D array.
Arrays.stream(attributes)
.map(Attribute::getCommand)
.filter(Optional::isPresent)
.map(Optional::get)
.flatMap((array) -> (Arrays.stream((String[]) array)))
.toArray(String[]::new)
Where Attribute
conforms to the following interface:
public interface Attribute<T> {
Optional<String[]> getCommand();
}
However, the final flatMap()
call isn't operating as expected.
.flatMap((array) -> (Arrays.stream((String[]) array)))
works just fine..flatMap((array) -> (Arrays.stream(array)))
fails to compile withjava: no suitable method found for stream(java.lang.Object)
..flatMap(Arrays::stream)
fails to compile withjava: incompatible types: cannot infer type-variable(s) T (argument mismatch; java.lang.Object cannot be converted to T[])
.
It seems to me that the type should be inferred just fine though. IntelliJ agrees and marks the cast as redundant and shows no compile errors with any of the three implementations. Why does Java require this apparently redundant typecast?
I additionally tried the following minimalist implementation:
import java.util.Arrays;
import java.util.Optional;
public class Streaming {
public static void main(String[] args) {
Optional<String[]>[] myarray = new Optional[]{Optional.of(new String[]{"Hello", "world"}),
Optional.empty(), Optional.of(new String[]{"Foo"})};
System.out.println(Arrays.toString(Arrays.stream(myarray).filter(Optional::isPresent).map
(Optional::get).flatMap(Arrays::stream).toArray(String[]::new)));
}
}
And it works just fine with all three implementations, outputting the expected [Hello, world, Foo]
.
Edit:
This was marked as a duplicate of this question. I may be wrong, but it seems that there's a distinction since this the type is specified in a more explicit manner. Notably, IntelliJ agrees that the cast is necessary in the example provided on said post, but not for my code. If I am mistaken, please let me know.
Edit:
Per request, the declaration of attributes
is Attribute[] attributes = new Attribute[]{...}
where ...
is a variety of implementations of Attribute.