前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >Carson带你学Android:什么时候应该使用Rxjava?(开发场景汇总)

Carson带你学Android:什么时候应该使用Rxjava?(开发场景汇总)

作者头像
Carson.Ho
发布2022-03-24 20:28:59
9430
发布2022-03-24 20:28:59
举报
文章被收录于专栏:Android知识分享

前言

  • Rxjava由于其基于事件流的链式调用、逻辑简洁 & 使用简单的特点,深受各大 Android开发者的欢迎。

今天,我将为大家带来 Rxjava的的基本使用 & 实际应用案例教学,即常见开发应用场景实现 ,并结合常用相关框架如Retrofit等,希望大家会喜欢。

Carson带你学RxJava系列文章,包括 原理、操作符、应用场景、背压等等,请看文章:Android:这是一份全面 & 详细的RxJava学习指南

目录

1. 简介

RxJava的简介如下

2. 基本使用

  • Rxjava的使用方式有两种: 方式1:分步骤实现

方式2:基于事件流的链式调用

3. 实际开发应用场景

  • RxJava的实际开发应用场景 与 其对应的操作符息息相关
  • 常见的RxJava实际开发应用场景有如下:
  • 下面,我将对每个实际开发应用场景进行实例讲解教学

下面实例皆结合常用框架如RetrofitRxBindingRxBus

3.1 网络请求轮询(无条件)

  • 需求场景

3.2 网路请求轮询(有条件)

  • 需求场景

3.3 网络请求出错重连

  • 需求场景
  • 功能需求说明
  • 功能逻辑

3.4 网络请求嵌套回调

  • 背景 需要进行嵌套网络请求:即在第1个网络请求成功后,继续再进行一次网络请求

如 先进行 用户注册 的网络请求, 待注册成功后回再继续发送 用户登录 的网络请求

  • 冲突 嵌套实现网络请求较为复杂,即嵌套调用函数

下面展示的是结合 RetrofitRxJava的基本用法,即未用操作符前

代码语言:javascript
复制
// 发送注册网络请求的函数方法
    private void register() {
        api.register(new RegisterRequest())
                .subscribeOn(Schedulers.io())               //在IO线程进行网络请求
                .observeOn(AndroidSchedulers.mainThread())  //回到主线程去处理请求结果
                .subscribe(new Consumer<RegisterResponse>() {
                    @Override
                    public void accept(RegisterResponse registerResponse) throws Exception {
                        Toast.makeText(MainActivity.this, "注册成功", Toast.LENGTH_SHORT).show();
                        login();   //注册成功, 调用登录的方法
                    }
                }, new Consumer<Throwable>() {
                    @Override
                    public void accept(Throwable throwable) throws Exception {
                        Toast.makeText(MainActivity.this, "注册失败", Toast.LENGTH_SHORT).show();
                    }
                });
    }


// 发送登录网络请求的函数方法
private void login() {
        api.login(new LoginRequest())
                .subscribeOn(Schedulers.io())               //在IO线程进行网络请求
                .observeOn(AndroidSchedulers.mainThread())  //回到主线程去处理请求结果
                .subscribe(new Consumer<LoginResponse>() {
                    @Override
                    public void accept(LoginResponse loginResponse) throws Exception {
                        Toast.makeText(MainActivity.this, "登录成功", Toast.LENGTH_SHORT).show();
                    }
                }, new Consumer<Throwable>() {
                    @Override
                    public void accept(Throwable throwable) throws Exception {
                        Toast.makeText(MainActivity.this, "登录失败", Toast.LENGTH_SHORT).show();
                    }
                });
    }

3.5 从磁盘 / 内存缓存中 获取缓存数据

  • 需求场景
  • 功能说明 对于从磁盘 / 内存缓存中 获取缓存数据 的功能逻辑如下:

3.6 合并数据源

  • 需求场景

3.7 联合判断

  • 需求场景 需要同时对多个事件进行联合判断

如,填写表单时,需要表单里所有信息(姓名、年龄、职业等)都被填写后,才允许点击 “提交” 按钮

  • 功能说明 此处采用 填写表单 作为联合判断功能展示,即,表单里所有信息(姓名、年龄、职业等)都被填写后,才允许点击 “提交” 按钮
  • 具体实现 Android RxJava 实际应用讲解:联合判断

3.8 线程控制(切换 / 调度 )

3.9 功能防抖

  • 需求场景
  • 功能说明

3.10 联想搜索优化

  • 需求场景
  • 功能说明

3.11 控制被观察者发送事件 & 观察者接收事件速度:背压

a. 背景

  • 观察者 & 被观察者 之间存在2种订阅关系:同步 & 异步。具体如下:
  • 对于异步订阅关系,存在 被观察者发送事件速度 与观察者接收事件速度 不匹配的情况
  • 发送 & 接收事件速度 = 单位时间内 发送&接收事件的数量
  • 大多数情况,主要是 被观察者发送事件速度 > 观察者接收事件速度

b. 冲突

  • 被观察者 发送事件速度太快,而观察者 来不及接收所有事件,从而导致观察者无法及时响应 / 处理所有发送过来事件的问题,最终导致缓存区溢出、事件丢失 & OOM
  • 如,点击按钮事件:连续过快的点击按钮10次,则只会造成点击2次的效果;
  • 解释:因为点击速度太快了,所以按钮来不及响应

下面再举个例子:

  • 被观察者的发送事件速度 = 10ms / 个
  • 观察者的接收事件速度 = 5s / 个

即出现发送 & 接收事件严重不匹配的问题

代码语言:javascript
复制
 Observable.create(new ObservableOnSubscribe<Integer>() {
            // 1. 创建被观察者 & 生产事件
            @Override
            public void subscribe(ObservableEmitter<Integer> emitter) throws Exception {

                for (int i = 0; ; i++) {
                    Log.d(TAG, "发送了事件"+ i );
                    Thread.sleep(10);
                    // 发送事件速度:10ms / 个 
                    emitter.onNext(i);

                }
                
            }
        }).subscribeOn(Schedulers.io()) // 设置被观察者在io线程中进行
                .observeOn(AndroidSchedulers.mainThread()) // 设置观察者在主线程中进行
             .subscribe(new Observer<Integer>() {
            // 2. 通过通过订阅(subscribe)连接观察者和被观察者
                 
            @Override
            public void onSubscribe(Disposable d) {
                Log.d(TAG, "开始采用subscribe连接");
            }

            @Override
            public void onNext(Integer value) {

                try {
                    // 接收事件速度:5s / 个 
                    Thread.sleep(5000);
                    Log.d(TAG, "接收到了事件"+ value  );
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }

            }

            @Override
            public void onError(Throwable e) {
                Log.d(TAG, "对Error事件作出响应");
            }

            @Override
            public void onComplete() {
                Log.d(TAG, "对Complete事件作出响应");
            }

        });
  • 结果 由于被观察者发送事件速度 > 观察者接收事件速度,所以出现流速不匹配问题,从而导致OOM

c. 解决方案

采用 背压策略

至此,关于RxJava常见的实际开发应用场景讲解完毕。

4. 总结

  • 本文主要对 RxJava2 中常用的实际开发应用场景讲解进行了详细介绍,下面用1张图进行总结
本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 前言
  • 目录
  • 1. 简介
  • 2. 基本使用
  • 3. 实际开发应用场景
    • 3.1 网络请求轮询(无条件)
      • 3.2 网路请求轮询(有条件)
        • 3.3 网络请求出错重连
          • 3.4 网络请求嵌套回调
            • 3.5 从磁盘 / 内存缓存中 获取缓存数据
              • 3.6 合并数据源
                • 3.7 联合判断
                  • 3.8 线程控制(切换 / 调度 )
                    • 3.9 功能防抖
                      • 3.10 联想搜索优化
                        • 3.11 控制被观察者发送事件 & 观察者接收事件速度:背压
                        • 4. 总结
                        领券
                        问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档