2

我试图弄清楚如何将可观察对象链接在一起。我有一个现有的方法:public static Observable<Data> getData(). 在我的另一堂课中,我有这个现有的代码:

doSomeBackgroundWork()
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Subscriber<..>() { ... })

我现在想将getData()呼叫链接到此呼叫。我该怎么做?我最初尝试过这个:

doSomeBackgroundWork()
.flatMap(s -> call() {
   mApi.getData()
}
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Subscriber<..>() { ... })

但这不起作用,因为 getData() 代码实际上是在主线程上执行的。

即使这样也行不通:

doSomeBackgroundWork()
.concatMap(s -> call() {
   mApi.getData()
}
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Subscriber<..>() { ... })

另外,当我尝试这个时,问题是这zipWith意味着两个 observables 并行运行,我真的希望一个接一个地运行。

doSomeBackgroundWork()
.zipWith(mApi.getData()),
    new Func2<BgWork, DataResponse,DataResponse>() {
    @Override
    public DataResponse call(BgWork bgWork, DatResponse data) {
       return data;
    }})
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Subscriber<..>() { ... })
4

1 回答 1

3

flatMapoperator 是这里的路,你只需要处理并发。如果你想getData()在调度程序上运行整个方法io,你可以在它observeOn之前应用运算符flatMap,然后在它之后再次应用,如下所示:

doSomeBackgroundWork()
  .observeOn(Schedulers.io())
  .flatMap(s -> call() {
       mApi.getData()
  }
  .subscribeOn(Schedulers.io())
  .observeOn(AndroidSchedulers.mainThread())
  .subscribe(new Subscriber<..>() { ... })

您会看到,subscribeOn操作员强制生产者“计算”并在提供的调度程序上发出数据,因此您在流组合中的哪个位置使用它并不重要,并且在多次使用时也没有效果。但运营商并非如此observeOn。它宁可告诉下一个流在另一个调度程序上执行工作。这意味着,当您稍后再次使用它时,您可以再次将计算转移到另一个调度程序。

但是,如果您只需要执行从getData()另一个调度程序上的方法返回的 observable 产生的工作,您可以subscribeOn在这个 observable 上使用,而不是在主流上使用。

doSomeBackgroundWork()
  .flatMap(s -> call() {
       mApi.getData().subscribeOn(Schedulers.io())
  }
  .subscribeOn(Schedulers.io())
  .observeOn(AndroidSchedulers.mainThread())
  .subscribe(new Subscriber<..>() { ... })
于 2017-01-10T20:06:54.780 回答