Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to preserve order of list after applying flatMap() to it?

Tags:

java

rx-java

The call to api.bookings returns a list of bookings in a predefined order. The call to api.order() returns a booking but with some extra info. After applying flatMap() the order of the bookings list gets messed up. (bookings.toList() is just a list if Bookings). How can I get the values in the zip function in the order as emitted by .from(bookings.toList()). Note: I can't use toSortedList as I have no way to compare two bookings.

bookingsSubscription = api.bookings()
                    .flatMap(bookings -> 
                        Observable.zip(
                            Observable 
                                .from(bookings.toList()) 
                                .flatMap(booking -> api.order(booking.orderId)),

                            Observable.from(bookings.toList()),

                            (newBooking, oldBooking) -> {
                               // at this point newBooking != oldBooking
                            }
                    ).toList())
                    .subscribe(callback);

api.order

like image 652
VM4 Avatar asked Dec 08 '14 09:12

VM4


People also ask

Does flatMap preserve order?

Does flatmap() method preserve the order of the streams? Yes, It does and map() also.

What is the difference between map() and flatMap()?

map() function produces one output for one input value, whereas flatMap() function produces an arbitrary no of values as output (ie zero or more than zero) for each input value. Where R is the element type of the new stream.

What does flatMap() do?

flatMap() is an intermediate operation and return a new Stream. It returns a Stream consisting of the results of replacing each element of the given stream with the contents of a mapped stream produced by applying the provided mapping function to each element.

How flatMap works in java?

In Java 8 Streams, the flatMap() method applies operation as a mapper function and provides a stream of element values. It means that in each iteration of each element the map() method creates a separate new stream. By using the flattening mechanism, it merges all streams into a single resultant stream.


1 Answers

concatMap will work but won't give the concurrency which you want. concatMapEager on the other hand will.

An equivalent option is to create a List<Observable> manually and use Observable.zip(Iterable, FuncN) to combine the list. This will have the same effect as concatMapEager.

See RxJava issue 3017 for a discussion.

like image 102
Alexander Torstling Avatar answered Sep 19 '22 16:09

Alexander Torstling