RX系列三 | RxJava | create | from | interval | just | range | filter


我们在第一篇里有说过一些基本的关系,现在我们需要用到一些依赖,这里记得添加,我们本章就来看下他的执行顺序和一些基本的操作符,操作符是我们一定要去摸清楚的,是很重要的知识点,操作符的作用是很大的

    compile 'io.reactivex:rxjava:1.1.0'
    compile 'io.reactivex:rxandroid:1.1.0'

首先,我们要明白,他的执行步骤是什么

执行步骤

与其说执行步骤,倒不如说执行流程,在RxJava中,我们首先,会创建一个Observable,也就是会观察者,去执行一定的逻辑,然后定义一个观察者Subscriber去接收结果,最后,通过

    observable.subscribe(showSub);

去订阅,而且很有意思的是,因为Rx的链式语法,我们可用一直next下去,这样,我们先来看一段简短的例子,你就明白大概的意思了,比如我现在要执行一个这样的操作

   //创建
    private void rxJavaCreate() {
        //定义被观察者
        Observable<String> observable = Observable.create(new Observable.OnSubscribe<String>() {
            @Override
            public void call(Subscriber<? super String> subscriber) {
                //判断是否有订阅的关系
                if (!subscriber.isUnsubscribed()) {
                    subscriber.onNext("Hello");
                    subscriber.onNext("Hi");
                    subscriber.onNext(getJson());
                    subscriber.onNext("END");
                    //完成
                    subscriber.onCompleted();
                }
            }
        });

        Subscriber<String> showSub = new Subscriber<String>() {
            //结束
            @Override
            public void onCompleted() {
                Log.i(TAG, "onCompleted");
            }

            //发生错误
            @Override
            public void onError(Throwable e) {
                Log.i(TAG, e.toString());
            }

            //继续执行
            @Override
            public void onNext(String s) {
                Log.i(TAG, s);
            }
        };
        //订阅
        observable.subscribe(showSub);
    }

    public static String getJson() {
        //这里进行网络解析 耗时操作
        return "Json Data";
    }

这段代码不难,你仔细去读,你就会发现,其实,这段代码就四个部分,首先是一个Observable,然后是一个Subscriber,接着就是订阅了。当然还有一个getJson的方法,那我们来具体分析一下这段代码吧,了解了这段代码,也就对RxJava有了一个皮毛的理解了

首先我们要看下Observable,他需要定义一个泛型的类型参数,默认是Object,这里我定义的是String,通过Observable.create去创建Observable对象,并且重写他里面的call方法,我们就可以在里面进行我们想要的操作了,先看下里面的这段代码

    //判断是否有订阅的关系
    if (!subscriber.isUnsubscribed()) {
         subscriber.onNext("Hello");
         subscriber.onNext("Hi");
         subscriber.onNext(getJson());
         subscriber.onNext("END");
         //完成
         subscriber.onCompleted()
     }

这段代码可以看出,我们首先来判断isUnsubscribed是否存在订阅关系,然后去执行,这里先是一个Hello,然后时一个Hi,接着调用getJson,最后END,看起来是这样,但是我要告诉你的是,如果getJson是一个网络请求的耗时操作,那他们的执行顺序是什么呢?其实他们还是顺序执行,最后调用的是subscriber.onCompleted()来告诉Subscriber,我已经OK了,那我们再看Subscriber就比较好说话了,他里面三个方法都不用多说了吧,一个是结束,一个是错误,还有一个继续执行,最后通过订阅就行,那我们来看下他真的执行打印顺序是什么呢?

可以看到,的确是顺序执行,最后,调用onCompleted的回调,流程算是清楚了吧,但是其实我们并没有讲真正的使用,不过在此之前,还是要说一下,RxJava的一个特点就是链式,也就是简洁,特别是配合了lambda表达式,那就更爽了,不过这个我们后面讲,先看一下传统的缩写是怎样的

    //链式表达
    private void  rxJavaCreateSmall(){
        Observable.create(new Observable.OnSubscribe<Integer>() {
            @Override
            public void call(Subscriber<? super Integer> subscriber) {
                for (int i = 0; i < 10; i++) {
                    subscriber.onNext(i);
                }
                //结束
                subscriber.onCompleted();
            }
        }).subscribe(new Subscriber<Integer>() {
            @Override
            public void onCompleted() {
                Log.i(TAG, "onCompleted");
            }

            @Override
            public void onError(Throwable e) {
                Log.i(TAG, e.toString());
            }

            @Override
            public void onNext(Integer integer) {
                Log.i(TAG, integer.toString());
            }
        });
    }

这样也是可以的,可以看到,我们执行了十次的onNext,看下并且这是一个链式表达,这就是一个整个的流程了,我们来看下执行结果:

from操作符

其实这里还有一种比较简单的方式就是用from操作符了,操作符和我们是密不可分的,所以我这里先提及一下,首先说一下from操作符的含义

  • 将其他种类的对象和数据类型转换为Observable,我们看一段代码来理解他
   //from操作符
    private void fromOperation(){
        Integer [] items = {1,2,3,4,5};
        //使用在被观察者,返回的对象一般都是数值类型
        Observable observable =Observable.from(items);
        observable.subscribe(new Action1() {
            @Override
            public void call(Object o) {
                Log.i(TAG,o.toString());
            }
        });
    }

当你使用Observable时,如果你要处理的数据都可以转换成为Observables,而不是需要混合使用Observables和其他类型的数据

使用在被观察者,返回的对象一般都是数值类型

interval操作符

form就是顺序的发送数据,其实还有一个操作符,也是可以的,那就是interval,指定某一时刻进行数据发送,有点类似与定时器,我们来看下这段代码

  //指定某一时刻进行数据发送
    private void intervalOperation(){
        //每隔一秒发送数据
        Observable observable =Observable.interval(1,1, TimeUnit.SECONDS);
        observable.subscribe(new Action1() {
            @Override
            public void call(Object o) {
                Log.i(TAG,o.toString());
            }
        });
    }

这段代码就是每隔一秒发送一个数据,我们默认是累加,主要还是在interval这个参数里面,我们看下效果

just操作符

前面两个都是处理整形的,但是如果你需要处理数组集合呢?这个时候你就需要用到just了,我们来看下他的实例代码

   //just操作符 处理数组集合
    private void justOperation(){
        Integer [] items1 = {1,2,3,4,5};
        Integer [] items2 = {6,7,8,9,10};
        Observable observable =Observable.just(items1,items2);
        observable.subscribe(new Subscriber<Integer[]>() {
            @Override
            public void onCompleted() {
                Log.i(TAG, "onCompleted");
            }

            @Override
            public void onError(Throwable e) {
                Log.i(TAG, e.toString());
            }

            @Override
            public void onNext(Integer[] i) {
                //这里是数组输出
                for (int j = 0; j < i.length; j++) {
                    Log.i(TAG, i[j].toString());
                }
            }
        });
    }

这里我们就是打印item1和item2的数据了,当然,我这里为什么传两个,你传一个也可以嘛,这只是一个参数而已,我们来看下他的运行结果

这里可以看到的是顺序执行,先item1再item2了

range操作符

其实在上面,还有一种没有说到,那就是指定范围内输出,就像interval一样,他是无限的累加,但是我现在输出的返回控制在一定的数据内中,这就要使用range了,我们来看下代码

     //范围输出
    private void rangeOperation(){
        Observable observable =Observable.range(1,10);
        observable.subscribe(new Subscriber<Integer>() {
            @Override
            public void onCompleted() {
                Log.i(TAG, "onCompleted");
            }

            @Override
            public void onError(Throwable e) {
                Log.i(TAG, e.toString());
            }

            @Override
            public void onNext(Integer i) {
                Log.i(TAG, i.toString());
            }
        });
    }

这里我指定输出范围是1-10,那么他执行的结果又会是什么呢?

可以看到,输出到10就没有再输出了

filter操作符

有范围输出,那肯定有过滤了,越看越觉得和String的方法有点像,但是你别忘记了,RxJava有一个特点就是异步,那里才是真正的有用的地方,现在我只是先把操作符的实例告诉大家,但是如果还没有运用到实际项目中去的话,你应该还属于半懵逼的状态,不过不要紧,我们继续看:说一下filter,他是过滤器,我们直接来看代码

    //过滤
    private void filterOperation(){
        Observable.just(1,2,3,4,5,6,7,8,9,10).filter(new Func1<Integer, Boolean>() {
            @Override
            public Boolean call(Integer integer) {
                return integer < 5;
            }
            //表示通过网络获取数据
        }).observeOn(Schedulers.io()).subscribe(new Subscriber<Integer>() {
            @Override
            public void onCompleted() {
                Log.i(TAG, "onCompleted");
            }

            @Override
            public void onError(Throwable e) {
                Log.i(TAG, e.toString());
            }

            @Override
            public void onNext(Integer integer) {
                Log.i(TAG, integer.toString());
            }
        });
    }

这里我就直接链式了,我们可以看到Observable.just处理一个数组,向观察者传递数据,然后观察者拿到数据之后过滤一下, return integer < 5,只有小于5的数据才会被处理,再接着订阅,所以可以看到,输出的结果就是这个样子了

像RxJava的操作符是有很多的,但是这里就不一一列举了,还是需要大家自己去理解,带个路就行,后面结合实例,我们再来回过头来看这些例子,你就明白了,这里我也找到一个RxJava操作符的一览,有兴趣的可以看下:

当然,你如果有兴趣的话,可以找张梯子就看一下JW大神的视频讲解:JW大神的视频教学

OK,我这一章就先到这里了,有兴趣的可以接着往下看

Sample下载:系列最后一篇提供

有兴趣的加群:555974449

RX系列三 | RxJava | create | from | interval | just | range | filter的更多相关文章

  1. RX系列四 | RxAndroid | 加载图片 | 提交表单

    RX系列四 | RxAndroid | 加载图片 | 提交表单 说实话,学RxJava就是为了我们在Android中运用的更加顺手一点,也就是RxAndroid,我们还是先一步步来,学会怎么去用的比较 ...

  2. Rx系列---响应式编程

    Rx是ReactiveX的简称,翻译过来就是响应式编程 首先要先理清这么一个问题:Rxjava和我们平时写的程序有什么不同.相信稍微对Rxjava有点认知的朋友都会深深感受到用这种方式写的程序和我们一 ...

  3. Rx系列二 | Observer | Observable

    Rx系列二 | Observer | Observable 上节课我们对RX的一些基本概念和使用JAVA代码实现了一个观察者,但是这只是对思路的一个讲解,在我们JAVA中,其实是已经封装好了观察者对象 ...

  4. RX系列一 | ReactiveX根源 | 观察者模式分析

    RX系列一 | ReactiveX根源 | 观察者模式分析 Rx的响应式编程算是很火了,对吧,但是我的工作基本上就不会接触,所以学习的比较晚,到现在才分享给大家,我们一点点的去学,当你看完这整个系列的 ...

  5. Istio的流量管理(实操一)(istio 系列三)

    Istio的流量管理(实操一)(istio 系列三) 使用官方的Bookinfo应用进行测试.涵盖官方文档Traffic Management章节中的请求路由,故障注入,流量迁移,TCP流量迁移,请求 ...

  6. 理解RxJava:(三)RxJava的优点

    理解RxJava:(三)RxJava的优点 在第一部分,讲解了RxJava的基本结构.在第二部分,展示了operators的强大之处.但是你们可能仍然没有被说服,也没有足够的理由信服.下面是一些能让你 ...

  7. linux磁盘管理系列三:LVM的使用

    磁盘管理系列 linux磁盘管理系列一:磁盘配额管理   http://www.cnblogs.com/zhaojiedi1992/p/zhaojiedi_linux_040_quota.html l ...

  8. DocX开源WORD操作组件的学习系列三

    DocX学习系列 DocX开源WORD操作组件的学习系列一 : http://www.cnblogs.com/zhaojiedi1992/p/zhaojiedi_sharp_001_docx1.htm ...

  9. 很有用的PHP笔试题系列三

    1. 什么事面向对象?主要特征是什么? 面向对象是程序的一种设计方式,它利于提高程序的重用性,使程序结构更加清晰.主要特征:封装.继承.多态. 2. SESSION 与 COOKIE的区别是什么,请从 ...

随机推荐

  1. ZOJ-1203 Swordfish---最小生成树

    题目链接: https://vjudge.net/problem/ZOJ-1203 题目大意: 给定平面上N个城市的位置,计算连接这N个城市所需线路长度总和的最小值. 思路: 模板题 最小生成树,Pr ...

  2. bs4解析要获取被注掉的部分需先将注释符号去掉

    <div class="xzcf-content"> <div id="sfxz"> <div class="main- ...

  3. Centos MySQL数据库迁移详细步骤

    其实迁移数据库,一般用sql文件就行,把A服务器数据库的表结构和数据等等导出,然后导入到B服务器数据库, 但是这次数据文件过大,大约有40个G,使用命令行导入,效果不是很好,经常在执行过程中报错.卡死 ...

  4. Java中List集合的三种遍历方式(全网最详)

    List集合在Java日常开发中是必不可少的,只要懂得运用各种各样的方法就可以大大提高我们开发的效率,适当活用各种方法才会使我们开发事半功倍. 我总结了三种List集合的遍历方式,下面一一来介绍. 首 ...

  5. MySQL高可用架构之MHA 原理与实践

    MHA简介 关于MHA MHA(Master HA)是一款开源的MySQL的高可用程序,它为MySQL主从复制架构提供了automating master failover 功能.MHA在监控到mas ...

  6. 两个css之间的切换

    需求: 头部两个按钮 两种样式之间的切换 解决办法: 结合JQ  三目运算 来处理 第一步: 把需要切换的样式设置为样式里背景,这样做的目的为了避免 js里出现过多 css代码 二来这样会显得更加的清 ...

  7. 四,前端---constructor与prototype

    这里对于constructor 和 prototype做一个简单的介绍,旨在让大家有一个简单的了解与认识 1:定义与用法 prototype:属性使您有能力向对象添加属性和方法. constructo ...

  8. 处处留心皆学问——由“display:inline-block;”导致的间距引发的思考。

    昨天在做一个demo时遇到了一个问题:我有五个li需要并排排列,然后自然而然的我给它们设了display:inline-block;但是,过了很久之后发现,除了我写的样式外,它默认有一个间距,我们都不 ...

  9. JS基本数据类型(typeof的返回结果)

    number(Infinity/NaN) string boolean function object(null.各种值装箱对象.内置对象.自定义对象) undefined 判断对象是否为某个[类/构 ...

  10. [JSOI2008]球形空间产生器

    Description 有一个球形空间产生器能够在n维空间中产生一个坚硬的球体.现在,你被困在了这个n维球体中,你只知道球 面上n+1个点的坐标,你需要以最快的速度确定这个n维球体的球心坐标,以便于摧 ...