L’énoncé suivant, bien que dépourvu de sens, semble syntaxiquement correct.
final Stream<LongStream> foobar = IntStream.empty()
.flatMap(x -> IntStream.empty()
.mapToObj(y -> IntStream.empty()
.mapToLong(z -> 1))); //compilation error here on `z -> 1`
Cependant, il ne compile pas, en retournant:
Java: types incompatibles: type de retour incorrect dans l'expression lambda aucune instance de type variable U ne existe de sorte que Java.util.stream.Stream soit conforme à Java.util.stream.IntStream
Cependant, si vous retardez la flatmap, tout fonctionne bien:
final Stream<LongStream> foobar = IntStream.empty()
.mapToObj(x -> IntStream.empty()
.mapToObj(y -> IntStream.empty()
.mapToLong(z -> 1)))
.flatMap(x -> x);
Quelle est la difference entre .mapToObj(..).flatMap(..)
et just .flatMap(..)
? Est-il possible d'éliminer l'appel extra flatmap?
.mapToObj(..).flatMap(..)
et .flatMap(..)
attendent des signatures complètement différentes.
.mapToObj(..).flatMap(..)
attend une fonction int -> Object
et une fonction Object -> Stream<?>
.
.flatMap(..)
attend une fonction int -> IntStream
.
Si vous décomposez votre code, vous passez une fonction int -> Stream<LongStream>
, qui n'est pas compatible avec une fonction int -> IntStream
.
Vous auriez le même erreur avec ce code simplifié:
IntStream.empty().flatMap(x -> Stream.of(LongStream.empty()));
J'ai restructuré votre méthode pour décomposer ce qu'elle fait:
IntFunction<LongStream> f1 = y -> IntStream.empty().mapToLong(z -> 1);
IntFunction<LongStream> f2 = x -> IntStream.empty().mapToObj(f1);
final Stream<LongStream> foobar = IntStream.empty().flatMap(f2);
Nous avons deux choses qui ne vont pas ici:
Le lambda de la ligne 2 ne renvoie pas une LongStream
, mais plutôt un Stream<LongStream>
, car nous convertissons chaque int
de notre flux en un LongStream
. Si vous souhaitez que ce soit une LongStream
unique, vous devez faire un flatMapToLong
.
La flatMap
de la ligne 3 attend une fonction int -> int
, ce que la vôtre ne fait pas. Cependant, vous pouvez utiliser mapToObj
à la place, qui utilise la méthode que vous fournissez.
Donc, la méthode corrigée serait:
IntFunction<LongStream> f1 = y -> IntStream.empty().mapToLong(z -> 1);
IntFunction<LongStream> f2 = x -> IntStream.empty().mapToObj(f1).flatMapToLong(i -> i);
final Stream<LongStream> foobar = IntStream.empty().mapToObj(f2);