RxScala doOnCompleted не срабатывает после вызова .take()

Я новичок в RxScala Observables и испытываю странное поведение при использовании комбинации take(n) и doOnCompleted().

Ниже у меня есть пример теста, в котором я считаю, что первая подписка верна (с take(2) в начале) и выводит все журналы для методов подписки, следующего, завершенного и отказа от подписки, однако второй тест (take(2) ) после doOnComplete) никогда не достигает методов doOnCompleted.

import rx.lang.scala.Observable

object Tester extends App {

    val obs = Observable.from(List(1,2,3,4))

    val obsAddMethodsCorrect = obs.take(2)
        .doOnSubscribe( println("subscribe") )
        .doOnNext( n => println(s"next $n") )
        .doOnError( e => println("error") )
        .doOnCompleted( println("completed") )
        .doOnUnsubscribe( println("unsubscribe") )

    val obsAddMethodsInCorrect = obs
        .doOnError( e => println("error") )
        .doOnCompleted( println("completed") )
        .take(2)
        .doOnNext( n => println(s"next $n") )
        .doOnUnsubscribe( println("unsubscribe") )
        .doOnSubscribe( println("subscribe") )

    obsAddMethodsCorrect.toBlocking.subscribe()
    println("")
    println("The above seems correct. Below seems incorrect")
    println("")
    obsAddMethodsInCorrect.toBlocking.subscribe()

}

текущий вывод вышеуказанного теста ниже.

subscribe
next 1
next 2
completed
unsubscribe

The above seems correct. Below seems incorrect

subscribe
next 1
next 2
unsubscribe

Почему doOnCompleted() не срабатывает во втором примере?


person user499882    schedule 26.04.2018    source источник


Ответы (1)


Оператор doOnCompleted() вызовет свое действие при запуске события onCompleted(). Однако, когда вы отписываетесь от наблюдателя до того, как он закончит отправку элементов, onCompleted() не сработает. Цепочка наблюдателей фактически отменена.

person Bob Dalgleish    schedule 26.04.2018
comment
Извините, может быть, я не совсем понимаю, но как перемещение позиции, где вызывается take, меняет результат? Например, obsAddMethodsCorrect вводит doOnCompleted. - person user499882; 27.04.2018
comment
В цепочке наблюдателя есть 2 части: часть до и часть после оператора take(). Оператор take() отпишется от наблюдаемого источника до того, как произойдет onCompleted(). Вниз по течению наблюдаемая, созданная оператором take(), выдаст количество элементов, за которыми следует onCompleted(). Первая часть цепочки не увидит операцию onCompleted(). - person Bob Dalgleish; 27.04.2018