Rxjava observeOn和subscribeOn在Retrofit中

时间:2017-12-05 02:58:21

标签: android retrofit2 rx-java2

observeOn : 此方法只是更改下游所有运营商的线程 (https://medium.com/upday-devs/rxjava-subscribeon-vs-observeon-9af518ded53a

调用API时,我想在IO线程上运行与服务器的通信,并希望在mainThread上处理结果。

我在许多教程中看到了以下代码,毫无疑问它是正确的。 但我的理解是相反的,所以我想知道我误解了什么。

requestInterface.callApi()
    .observeOn(AndroidSchedulers.mainThread())
    .subscribeOn(Schedulers.io())
    .subscribe())

observeOn(AndroidSchedulers.mainThread())

:observeOn更改下游所有运算符的线程,但在本例中,实际的调用API函数是否高于observeOn?

.subscribeOn(Schedulers.io())

:奇怪的是,它需要在主线程上订阅,但在IO线程上订阅?

请告诉我我的误解是什么?

4 个答案:

答案 0 :(得分:3)

基本,我们会有

Observable.subscribe(Observer);// => Observer observe Observable and Observable subscribe Observer

实施例

requestInterface.callApi().subscribe(new Observer...); // requestInterface.callApi() <=> Observable

来自http://reactivex.io/documentation/operators/subscribeon.html

<强> SubscribeOn

  
      
  • SubscribeOn运算符指定 Observable 将开始运行的线程,无论运算符链中的哪个运算符被调用
  •   

ObserveOn (影响2件事)

  
      
  • 它指示 Observable 向指定的调度程序上的观察者发送通知。

  •   
  • ObserveOn影响 Observable 将在该操作符出现的位置使用的线程

  •   

实施例

registerUserReturnedObserverble()  // run on worker thread because subscribeOn(Schedulers.io()) (line 5)
.andThen(loginReturnObserverble()) // run on worker thread because subscribeOn(Schedulers.io()) (line 5)
.observeOn(AndroidSchedulers.mainThread())
.andThen(getUserDataReturnObserverble()) // run on main thread because .observeOn(AndroidSchedulers.mainThread()) is above this operator (line 3)
.subscribeOn(Schedulers.io())
.subscribe(new Observer<Void>{
    // run on main thread because observeOn(AndroidSchedulers.mainThread()) 
});

答案 1 :(得分:0)

以下是一个示例:

      getCardsObservable.subscribeOn(Schedulers.io())
            .observeOn(AndroidSchedulers.mainThread())
            .subscribe(new rx.Observer<List<Card>>() {
                @Override
                public void onCompleted() {

                }

                @Override
                public void onError(Throwable e) {
                    listener.onError(e.getMessage());
                }

                @Override
                public void onNext(List<Card> cards) {
                    listener.onSuccess(cards);
                }
            });

subscribeOn - &gt;将执行调用的线程类似于调用asynctask observeOn - &gt;在哪里回应将观察一个过程ui线程

订阅 - &gt;观察者回调

答案 2 :(得分:0)

  • subscribeOn(Schedulers.io()):这告诉Observable在后台线程上运行任务
  • observeOn(AndroidSchedulers.mainThread()):这告诉Observer在android UI线程上接收数据,以便您可以采取任何与UI相关的操作。

答案 3 :(得分:0)

以下情况指定了使用observeOn()和/或subscribeOn()时可能出现的所有不同情况。

  1. subscribeOn影响上游运营商(subscribeOn上方的运营商)
  2. observeOn影响下游运算符(observeOn下面的运算符)
  3. 如果您未在RxJava中指定线程(如果您未指定subscribeOnobserveOn或两者均未指定),则数据将由当前的调度程序/线程发出并处理(通常是主线程)。例如,下面链中的所有运算符都将由当前线程处理(Android为Main线程)。
Observable
.just("big", "bigger", "biggest")    
.map(String::length)    
.filter { it > 6 }    
.subscribe { length -> println("item length $length") }
  1. 如果仅指定subscribeOn,则将在该线程上执行所有运算符

    在此处输入代码

Observable
.just("big", "bigger", "biggest") 
.subscribeOn(Schedulers.io())    
.map(String::length)    
.filter { it > 6 }    
.subscribe { length -> println("item length $length") }

仅发出数据,映射和过滤器运算符将在io调度程序上按照上游运算符subscribeOn的指示执行。

  1. 如果仅指定observeOn,则所有运算符将在当前线程上执行,只有observeOn以下的运算符将切换到observeOn指定的线程。
Observable
.just("big", "bigger", "biggest")   
.map(String::length)
.observeOn(Schedulers.computation())     
.filter { it > 6 }    
.subscribe { length -> println("item length $length") }

仅发射数据,映射将在currentThread调度程序上执行。

过滤器将按照下游运算符observeOn的指示在计算调度程序上执行。

  1. 如果同时指定了subscribeOnobserveOn,则observeOn下的所有运算符都将切换到observeOn指定的线程,其余所有{{ 1}}切换到observeOn指定的线程。无论您指定subscribeOnsubscribeOn
  2. 的顺序如何,这都是正确的
observeOn

仅数据发射和map运算符将在io调度程序上按照上游运算符Observable .just("big", "bigger", "biggest") .subscribeOn(Schedulers.io()) .map(String::length) .observeOn(Schedulers.computation()) .filter { it > 6 } .subscribe { length -> println("item length $length") } 的指示执行。

过滤器将按照下游运算符subscribeOn的指示在计算调度程序上执行。

即使在observeOn之后调用subscribeOn,线程用法也将相同。

observeOn
相关问题