• 4. RxJava过滤操作符


    过滤操作符主要用于对事件数据的筛选过滤,只返回满足我们条件的数据。

    一. 根据指定条件过滤事件

    通过设置指定的条件,仅发送符合条件的事件

    1.Filter()

    filter(Func1)用来过滤观测序列中我们不想要的值,制返回满足条件的值

    1. Observable.create((ObservableOnSubscribe<Integer>) emitter -> {
    2. //1.发送3个事件
    3. emitter.onNext(1);
    4. emitter.onNext(2);
    5. emitter.onNext(3);
    6. }).filter(integer -> {
    7. //2.根据返回的integer值,采用filter对被观察者发送的事件进行过滤 & 筛选
    8. //a.返回true, 则继续发送
    9. //b.返回false, 则不发送(即过滤)
    10. return integer <3; // 本例中过滤了整数≥3的数据并重写发送给观察者
    11. }).subscribe(integer -> {
    12. //3.接收最新被观察者发送来的数据
    13. System.out.println("最终接收的数据: " + integer);
    14. });
    15. //执行结果
    16. 最终接收的数据: 1
    17. 最终接收的数据: 2

    2.ofType()

    它是filter的特殊形式,用于过滤 特定数据类型 的数据

    1. Observable.just(1, "3", true, 0.2f).ofType(Float.class) //筛选出浮点型数据
    2. .subscribe(aFloat -> System.out.println("获取到的浮点型事件元素是: " + aFloat));
    3. //执行结果
    4. 获取到的浮点型事件元素是: 0.2

    3.skip()/ skipLast()

    skip(int)让我们可以忽略Observable发射的前n项数据。只保留之后的数据。

    使用 skipLast() 操作符修改原始Observable,你可以忽略Observable'发射的后N项数据,只保留前面的数据。

    1. //使用1: 根据顺序跳过数据项
    2. Observable.just(1, "3", true, 0.2f)
    3. .skip(1) //跳过前1项
    4. .skipLast(2) //跳过后2项
    5. .subscribe(element -> System.out.println("获取到的事件元素是: " + element));
    6. //执行结果
    7. 获取到的事件元素是: 3
    8. // 使用2:根据时间跳过数据项
    9. // 发送事件特点:发送数据0-5,每隔1s发送一次,每次递增1;第1次发送延迟0s
    10. Observable.intervalRange(0, 5, 0, 1, TimeUnit.SECONDS)
    11. .skip(1, TimeUnit.SECONDS) // 跳过第1s发送的数据
    12. .skipLast(1, TimeUnit.SECONDS) // 跳过最后1s发送的数据
    13. .subscribe(along -> System.out.println("Time 获取到的整型事件元素是: " + along));
    14. try {
    15. Thread.sleep(8000);
    16. } catch (InterruptedException e) {
    17. e.printStackTrace();
    18. }
    19. //运行结果
    20. Time 获取到的整型事件元素是: 2
    21. Time 获取到的整型事件元素是: 3

    4.distinct() / distinctUntilChanged()

    过滤事件序列中重复的事件 / 连续重复的事件

    distinct()的过滤规则是只允许还没有发射过的数据通过,所有重复的数据项都只会发射一次。

    参数中的Func1中的call方法会根据Observable发射的值生成一个Key,然后比较这个key来判断两个数据是不是相同;如果判定为重复则会和distinct()一样过滤掉重复的数据项。

    1. Observable.just(1, 2, 3, 1, 4)
    2. .distinct()
    3. .subscribe(element -> System.out.println("获取到的事件元素是: " + element));
    4. //执行结果
    5. 获取到的事件元素是: 1
    6. 获取到的事件元素是: 2
    7. 获取到的事件元素是: 3
    8. 获取到的事件元素是: 4

    distinctUntilChanged()它只判定Observable发射的当前数据项和前一个数据项是否相同。

    1. Observable.just(1, 2, 3, 1, 4)
    2. .distinctUntilChanged()
    3. .subscribe(element -> System.out.println("获取到的事件元素是: " + element));
    4. //执行结果
    5. 获取到的事件元素是: 1
    6. 获取到的事件元素是: 2
    7. 获取到的事件元素是: 3
    8. 获取到的事件元素是: 1
    9. 获取到的事件元素是: 4

    二. 根据指定 事件数量 过滤事件

    通过设置指定的事件数量,仅发送特定数量的事件

    1.take(int)

    take(int)用一个整数n作为一个参数,只返回原始的序列中前N项数据,然后发射完成通知,忽略剩余的数据。

    1. Observable.just(1, 2, 3, 1, 4)
    2. .take(1)
    3. .subscribe(element -> System.out.println("获取到的事件元素是: " + element));
    4. //执行结果
    5. 获取到的事件元素是: 1

    2.takeLast(int)

    takeLast(int)用一个整数n作为一个参数,只返回原始的序列中后N项数据,然后发射完成通知,忽略前面的数据。

    1. Observable.just(1, 2, 3, 1, 4)
    2. .takeLast(2)
    3. .subscribe(element -> System.out.println("获取到的事件元素是: " + element));
    4. //执行结果
    5. 获取到的事件元素是: 1
    6. 获取到的事件元素是: 4

    三. 根据指定 时间 过滤事件

    通过设置指定的时间,仅发送在该时间内的事件

    1.throttleFirst() / throttleLast

    在某段时间内,只发送该段时间内第1次事件 / 最后1次事件

    如,1段时间内连续点击按钮,但只执行第1次的点击操作

    1. //在某一时段内,只发送该段时间内第1次事件
    2. Observable.create((ObservableOnSubscribe<Integer>) e -> {
    3. //隔段事件发送时间
    4. e.onNext(1);
    5. Thread.sleep(500);
    6. e.onNext(2);
    7. Thread.sleep(400);
    8. e.onNext(3);
    9. Thread.sleep(300);
    10. e.onNext(4);
    11. Thread.sleep(300);
    12. e.onNext(5);
    13. Thread.sleep(500);
    14. }).throttleFirst(1, TimeUnit.SECONDS) //每1秒采用第一条数据
    15. .subscribe(element -> System.out.println("获取到的事件元素是: " + element));
    16. //执行结果
    17. 获取到的事件元素是: 1
    18. 获取到的事件元素是: 4
    19. Observable.create(new ObservableOnSubscribe<Integer>() {
    20. @Override
    21. public void subscribe(@NonNull ObservableEmitter<Integer> e) throws Exception {
    22. //隔段事件发送时间
    23. e.onNext(1);
    24. Thread.sleep(500);
    25. e.onNext(2);
    26. Thread.sleep(400);
    27. e.onNext(3);
    28. Thread.sleep(300);
    29. e.onNext(4);
    30. Thread.sleep(300);
    31. e.onNext(5);
    32. Thread.sleep(500);
    33. }
    34. }).throttleLast(1, TimeUnit.SECONDS) //每1秒采用最后1条数据
    35. .subscribe(element -> System.out.println("获取到的事件元素是: " + element));
    36. //执行结果
    37. 获取到的事件元素是: 3
    38. 获取到的事件元素是: 5

    2.sample()

    在某段时间内,只发送该段时间内最新(最后)1次事件,与 throttleLast() 操作符类似,仅需要把上文的 throttleLast() 改成 Sample() 操作符即可;

    3.debounce() / throttleWithTimeout()

    发送数据事件时,若2次发送事件的间隔<指定时间,就会丢弃前一次的数据,直到指定时间内都没有新数据发射时才会发送后一次的数据debounce(long, TimeUnit)过滤掉了由Observable发射的速率过快的数据;如果在一个指定的时间间隔过去了仍旧没有发射一个,那么它将发射最后的那个。通常我们用来结合RxBing(Jake Wharton大神使用RxJava封装的Android UI组件)使用,防止button重复点击.

    1. //在某一时段内,只发送该段时间内最后1次事件
    2. Observable.create(new ObservableOnSubscribe() {
    3. @Override
    4. public void subscribe(@NonNull ObservableEmitter e) throws Exception {
    5. //隔段事件发送时间
    6. // 隔段事件发送时间
    7. e.onNext(1);
    8. Thread.sleep(500);
    9. e.onNext(2); // 1和2之间的间隔小于指定时间1s,所以前1次数据(1)会被抛弃,2会被保留
    10. Thread.sleep(1500); // 因为2和3之间的间隔大于指定时间1s,所以之前被保留的2事件将发出
    11. e.onNext(3);
    12. Thread.sleep(1500); // 因为3和4之间的间隔大于指定时间1s,所以3事件将发出
    13. e.onNext(4);
    14. Thread.sleep(500); // 因为4和5之间的间隔小于指定时间1s,所以前1次数据(4)会被抛弃,5会被保留
    15. e.onNext(5);
    16. Thread.sleep(500); // 因为5和6之间的间隔小于指定时间1s,所以前1次数据(5)会被抛弃,6会被保留
    17. e.onNext(6);
    18. Thread.sleep(1500); // 因为6和Complete实践之间的间隔大于指定时间1s,所以之前被保留的6事件将发出
    19. e.onComplete();
    20. }
    21. }).debounce(1, TimeUnit.SECONDS) //每1秒采用最后1条数据 换成 throttleWithTimeout
    22. .subscribe(element -> System.out.println("获取到的事件元素是: " + element));
    23. //执行结果
    24. 获取到的事件元素是: 2
    25. 获取到的事件元素是: 3
    26. 获取到的事件元素是: 6

    四. 根据指定 事件位置 过滤事件

    1.fristElement() / lastElement()

    仅选取第1个元素 / 最后一个元素

    1. Observable.just(1, 2, 3, 4)
    2. .firstElement() //获取第一个元素 .lastElement 获取最后一个元素
    3. .subscribe(element -> System.out.println("获取到的事件元素是: " + element));

    2.elementAt()

    elementAt(int)用来获取元素Observable发射的事件序列中的第n项数据,并当做唯一的数据发射出去

    1. Observable.just(1, 2, 3, 4)
    2. .elementAt(2)
    3. .subscribe(element -> System.out.println("获取到的事件元素是: " + element));

    3.elementAtOrError()

    在elementAt()的基础上,当出现越界情况(即获取的位置索引 > 发送事件序列长度)时,即抛出异常

    1. Observable.just(1, 2, 3, 4)
    2. .elementAtOrError(5)
    3. .subscribe(element -> System.out.println("获取到的事件元素是: " + element));
    4. //返回结果
    5. io.reactivex.exceptions.OnErrorNotImplementedException
    ​​​​​​​

    参考资料: 过滤操作符 过滤操作符2 过滤操作符3

  • 相关阅读:
    XSS原理
    2023最新SSM计算机毕业设计选题大全(附源码+LW)之java教学信息管理辅助系统jszpb
    【蓝桥每日一题]-前缀和与差分(保姆级教程 篇2)#差分序列
    基于Java汽车租赁系统设计实现(源码+lw+部署文档+讲解等)
    【软件测试笔试题】阿里巴巴(中国)网络技术有限公司
    提取文章中关键词综述
    JS——数组相关知识点汇总
    java数据结构与算法刷题-----LeetCode27:移除元素
    excel怎么设置任意选一个单元格纵横竖横都有颜色
    Xmake 和 C/C++ 包管理
  • 原文地址:https://blog.csdn.net/x910131/article/details/126071001