RxJava2.X使用小记

Transformer转换器,Observable.compose()

Observable.compose()操作符是直接对当前Observable进行操作;
Transformer实际上就是Func1<Observable,Observable>,换句话说就是提供给他一个Observable它会返回给你另一个Observable。ObservableTransformer、SingleTransformer、FlowableTransformer
创建一个SingleTransformer调度器:

    <T> SingleTransformer<T, T> applySchedulers() {  
      return new SingleTransformer<T, T>() {
        @Override
        public Observable<T> call(Single<T> single) {
          return single
            .subscribeOn(Schedulers.io())
            .observeOn(AndroidSchedulers.mainThread())
            .compose(bindUntilEvent(FragmentEvent.STOP));//内部也是转换器
        }
      };
    }

doOnSubscribe、doFinally

RetrofitHelper.getHiboxService().getOpSaveOrderInfo(PbOpenPlatformHelper.getSaveOrderInfoReq(saveCode))
                .compose(bindUntilEvent(FragmentEvent.STOP))
                .subscribeOn(Schedulers.io())//指定getOpSaveOrderInfo线程
                .doOnSubscribe(disposable1 -> UiUtil.netDialogShow(sfDialog, getActivity()))//订阅即执行
                .subscribeOn(AndroidSchedulers.mainThread())//指定doOnSubscribe的线程
                .observeOn(AndroidSchedulers.mainThread())//指定doFinally,subscribe()的线程
                .doFinally(() -> UiUtil.netDialogDiss(sfDialog, getActivity()))//订阅结束,无论异常还是成功
                .subscribe(saveCodeOrderInfoResp -> {
                            
                        }, throwable -> {
                           
                        }
                );

compose()和flatMap()

compose()和flatMap()都是发射出Observable,不同于map、flatMap等lift操作改变Observable发布的事件及序列,compose操作符是直接对当前Observable进行操作。

1.compose() 是唯一一个能从流中获取原生Observable 的方法,因此,影响整个流的操作符(像subscribeOn()和observeOn())需要使用compose(),相对的,如果你在flatMap()中使用subscribeOn()/observeOn(),它只影响你创建的flatMap()中的Observable,而不是整个流。
2.当你创建一个Observable流并且内联了一堆操作符以后,compose()会立即执行,flatMap()则是在onNext()被调用以后才会执行,换句话说,flatMap()转换的是每个项目,而compose()转换的是整个流。
3.flatMap()一定是低效率的,因为他每次调用onNext()之后都需要创建一个新的Observable,compose()是操作在整个流上的。

Subject

在RxJava2.x中,官方一共为我们提供了以下几种Subject:

    ReplaySubject (释放接收到的所有数据)
    BehaviorSubject (释放订阅前最后一个数据和订阅后接收到的所有数据)
    PublishSubject (释放订阅后接收到的数据)
    AsyncSubject (仅释放接收到的最后一个数据)
    SerializedSubject(串行Subject)
    UnicastSubject (仅支持订阅一次的Subject)

ReplaySubject 无论是在接收到数据前还是数据后订阅,ReplaySubject都会发射所有数据给订阅者:通过一个List动态存储所有接收到的数据,当被订阅时,将所有的数据都发送给订阅者。

BehaviorSubject其原理就是通过subscribers这个核心的成员,它是一个不断变化的数组。在创建时,其内部只是一个EMPTY(BehaviorDisposable)对象,每次被订阅,都会在既有的数组上新加一个BehaviorDisposable对象,这个对象中包含了一个List,存储之后会收到的数据。
同时,BehaviorSubject还有一个value的成员,该成员会随着数据的不断接收而进行更新,它总是记录着当前最后一个接收到的数据,当被subscribe时,会执行emitFirst()方法,发射当前记录的数据,也就是订阅前接收到的最后一个数据。RxLifecycle核心类

PublishSubject 其原理就是通过subscribers这个核心的成员,它是一个不断变化的数组。在创建时,其内部只是一个EMPTY(BehaviorDisposable)对象,每次被订阅,都会在既有的数组上新加一个BehaviorDisposable对象,这个对象中包含了一个List,存储之后会收到的数据。RxBus事件总线核心类

TakeUntil、TakeWhile

TakeUntil使用一个标志Observable是否发射数据来判断,当标志Observable没有发射数据时,正常发射数据,而一旦标志Observable发射过了数据则后面的数据都会被丢弃。

        Observable.interval(1, TimeUnit.SECONDS).takeUntil(Observable.timer(3, TimeUnit.SECONDS)) //延迟3s
                .subscribe(new Consumer<Long>() {
                    @Override
                    public void accept(Long aLong) throws Exception {
                        Log.d("takeUntil", "aLong = " + aLong); //0,1
                    }
                });

TakeWhile则是根据一个函数来判断是否发射数据,当函数返回值为true的时候正常发射数据;当函数返回false的时候丢弃所有后面的数据。

        Observable.fromArray(new Integer[]{1, 2, 3, 4, 5, 6, 5, 4, 3, 2, 1}).takeWhile(new Predicate<Integer>() {
            @Override
            public boolean test(Integer integer) throws Exception {//1,2,3,4,5
                Log.d("takeWhile", "integer -> " + integer); //如果首次为false后面的将不进行判断
                return integer < 5; //
            }

        }).subscribe(new Consumer<Integer>() {
            @Override
            public void accept(Integer integer) throws Exception {
                Log.d("takeWhile", "integer = " + integer); //1,2,3,4
            }
        });

RxLifecycle

先来看一下RxLifecycle的使用:

RetrofitHelper.getHiboxService().getOpSaveOrderInfo()
                .compose(bindUntilEvent(FragmentEvent.STOP))//RxLifecycle绑定生命周期,stop时停止订阅
                .subscribeOn(Schedulers.io())
                .observeOn(AndroidSchedulers.mainThread())
                .subscribe(saveCodeOrderInfoResp -> {
         
                        }, throwable -> {

                        }
                );

在RxFragment中创建了BehaviorSubject,并在Fragment生命周期方法中onNext对应事件

    private final BehaviorSubject<FragmentEvent> lifecycleSubject = BehaviorSubject.create();

    @Override
    @NonNull
    @CheckResult
    public final <T> LifecycleTransformer<T> bindUntilEvent(@NonNull FragmentEvent event) {
        return RxLifecycle.bindUntilEvent(lifecycleSubject, event);
    }

    @Override
    public void onStop() {
        lifecycleSubject.onNext(FragmentEvent.STOP);
        super.onStop();
    }

在RxLifecycle中使用filter操作符过滤事件,并创建了转换器LifecycleTransformer

public static <T, R> LifecycleTransformer<T> bindUntilEvent(@Nonnull final Observable<R> lifecycle,
                                                                @Nonnull final R event) {
        checkNotNull(lifecycle, "lifecycle == null");
        checkNotNull(event, "event == null");
        return bind(takeUntilEvent(lifecycle, event));
    }

    private static <R> Observable<R> takeUntilEvent(final Observable<R> lifecycle, final R event) {
        return lifecycle.filter(new Predicate<R>() {
            @Override
            public boolean test(R lifecycleEvent) throws Exception {
                return lifecycleEvent.equals(event);
            }
        });
    }
  public static <T, R> LifecycleTransformer<T> bind(@Nonnull final Observable<R> lifecycle) {
        return new LifecycleTransformer<>(lifecycle);
    }

在LifecycleTransformer中继续使用takeUntil操作符,结合compose控制事件是否继续流转。

combineLatest与zip

combineLatest接受两个或以上的Observable和一个FuncX闭包。当传入的Observable中任意的一个发射数据时,combineLatest将每个Observable的最近值(Lastest)联合起来(combine)传给FuncX闭包进行处理。

zip是严格按照顺序来组合每个Observable,比如ObservableA的第一个数据和ObservableB的第一个数据组合在一起发射给FuncX来处理,两者的第N个数据组合在一起发射给FuncX来处理; zip并不是任意一个Observable发射数据了就触发闭包处理,而是等待每个Observable的第N个数据都发射齐全了才触发。

  Flowable<String> phoneFlowable = Flowable.create(emitter -> RxTextView.afterTextChangeEvents(et_forget_hone)
                .subscribe(textViewAfterTextChangeEvent -> {
                    String phone = textViewAfterTextChangeEvent.toString().trim();
                    btn_get_vercode.setEnabled(PhoneUtils.isMobileChina(phone));
                    emitter.onNext(phone);
                }), BackpressureStrategy.LATEST);

        Flowable<String> vercodeFlowable = Flowable.create(emitter -> RxTextView.afterTextChangeEvents(et_op_vercode)
                .subscribe(textViewAfterTextChangeEvent -> {
                    String verifyCode = textViewAfterTextChangeEvent.toString().trim();
                    emitter.onNext(verifyCode);
                }), BackpressureStrategy.LATEST);


        Disposable disposable = Flowable.combineLatest(phoneFlowable, vercodeFlowable, (phone, vercode)
                -> !StringUtils.isEmpty(phone) && !StringUtils.isEmpty(vercode))
                .subscribe(btn_op_save_list::setEnabled);


        Disposable disposable1 =  Flowable.zip(phoneFlowable, vercodeFlowable, (s, s2)
                -> s+s2).
                subscribe(s -> {
                
        });
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 160,026评论 4 364
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 67,655评论 1 296
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 109,726评论 0 244
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 44,204评论 0 213
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 52,558评论 3 287
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 40,731评论 1 222
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 31,944评论 2 314
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 30,698评论 0 203
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 34,438评论 1 246
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 30,633评论 2 247
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 32,125评论 1 260
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 28,444评论 3 255
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 33,137评论 3 238
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 26,103评论 0 8
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 26,888评论 0 197
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 35,772评论 2 276
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 35,669评论 2 271

推荐阅读更多精彩内容