2

The structure:

The api.vehicles() endpoint returns a list of ids. The api.driveState(int id) returns a state for a vehicle with the id as parameter.

What I need:

Make a call to the .vehicles(). For the returned ids, make a call per id on the .driveState(id) endpoint and wait for all the calls to succeed and return a list of states together. Let's ignore the retrys() and network failures for now.

What I have tried is:

api.vehicles()
    .flatMap(vehicles -> merge(getVehicleStates(vehicles)))
    .toList()
    .doOnNext(driveStates -> {

    });

where getVehicleStates() is:

private List<Observable<DriveState>> getVehicleStates(List<Vehicle> vehicles){
    List<Observable<DriveState>> states = new ArrayList<>();
    for (Vehicle vehicle : vehicles) {
        states.add(api.driveState(vehicle.getId()));
    }
    return states;
}

What would have been better I believe is the .zip() function. However I do not know how to deal with the FuncN() method:

api.vehicles()
        .flatMap(vehicles -> 
                zip(getVehicleStates(vehicles), new FuncN<DriveState>() {
                    @Override public DriveState call(Object... args) {
                        return null;
                    }
                }
        ));

PS: slightly similar but unanswered: Combining 'n' Observables of the same type (RxJava)

Community
  • 1
  • 1
Diolor
  • 13,181
  • 30
  • 111
  • 179
  • `zip` sure looks like it's what you're after. You're just having trouble dealing with FuncN? What trouble? – Adam S Jun 07 '15 at 16:17
  • If it's the first time you've seen varargs, [check out this question](http://stackoverflow.com/questions/16674023/proper-terminology-for-object-args) :) – Adam S Jun 07 '15 at 16:22
  • @AdamS Well the problem is that the varargs are of `Object` class and not of the specified `DriveState`. – Diolor Jun 07 '15 at 17:32
  • Yeah, you can do a for each and cast it. – Adam S Jun 07 '15 at 17:48

1 Answers1

0

The zip(Iterable, FuncN) operator will zip your observables, and supply the results of all of them in the Object.. args.

It looks like you're looking for a list of all DriveState - this is what you've got in args. The documentation for varargs explains that this is, effectively, an array of Object, whose construction is conveniently hidden by the ... syntax.

You can use zip to get a list of all the DriveState as follows:

zip(getVehicleStates(vehicles), new FuncN<List<DriveState>>() {
    @Override public List<DriveState> call(Object... args) {
        return Arrays.asList((DriveState[])args);
    }
}

Of course, you might want to operate on the DriveState objects and return some modification to them or some result object etc instead of the list.

Adam S
  • 16,144
  • 6
  • 54
  • 81