如何使用RxJava重复网络调用

时间:2016-10-21 02:01:08

标签: java android retrofit rx-java rx-android

我有一个API,可以让我通过id使用以下内容检索项目:

http://myapi.com/api/v1/item/1

最后一个值是项目的id。这很好,花花公子,我可以编写一个Retrofit服务接口并调用这样的项目:

MyService service = MyService.retrofit.create(MyService.class);

service.itemById(1)
                .observeOn(AndroidSchedulers.mainThread())
                .subscribeOn(Schedulers.io())
                .subscribe(new Subscriber<Item>() {
                    @Override
                    public void onCompleted() {

                    }

                    @Override
                    public void onError(Throwable e) {
                        Log.v(LOG_TAG, e.getMessage());
                    }

                    @Override
                    public void onNext(Item item) {
                        adapter.addItem(item);
                    }
                });

我遇到的问题是我想一次检索5个项目,但我不知道如何做到这一点。例如,如果我想获取ID为1,2,3,4,5的项目,我该如何在一个组中执行此操作?我已经查看了Observable.zip(),但我无法弄清楚如何设置它。

2 个答案:

答案 0 :(得分:4)

如果你想使用zip,你想做类似的事情(简洁的lambda语法):

Observable.zip(
    service.itemById(1),
    service.itemById(2),
    service.itemById(3),
    service.itemById(4),
    service.itemById(5),
    (i1, i2, i3, i4, i5) -> new Tuple<>(i1, i2, i3, i4, i5))
    .observeOn(AndroidSchedulers.mainThread())
    .subscribeOn(Schedulers.io())
    .subscribe(
        tuple -> {
            // < use the tuple >
        },
        error -> {
            // ...
        }
    );

注意:您必须创建Tuple类或其他对象,或者导入Tuple库。

另一种基于您的评论的变体:

Observable.range(1, 5)
    .flatMap(t -> service.itemById(t), (i, response) -> new Tuple<>(i, response))
    .subscribeOn(Schedulers.io())
    .subscribe...

这将并行运行您的请求,您的订阅块将分别接收每个元素。

Observable.range(1, 5)
    .flatMap(t -> service.itemById(t), (i, response) -> new Tuple<>(i, response))
    .collect(ArrayList::new, ArrayList::add)
    .subscribeOn(Schedulers.io())
    .subscribe...

这将在数组中收集生成的元组。

答案 1 :(得分:0)

可观察&LT;列表与LT; YourType&GT;&GT; list = Observable.range(/ ... /)。map(/ ... /)。toList();