实例讲解丨使用RxJava的最佳开发场景

Posted 可能科技

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了实例讲解丨使用RxJava的最佳开发场景相关的知识,希望对你有一定的参考价值。

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


本文章主要基于 Rxjava 2.0 。为大家讲解 Rxjava的的基本使用 & 实际应用案例教学,即常见开发应用场景实现 ,并结合常用相关框架如Retrofit等。



目录

实例讲解丨使用RxJava的最佳开发场景



1
简介


RxJava的简介如下

实例讲解丨使用RxJava的最佳开发场景



2
基本使用



  • Rxjava的使用方式有两种: 


方式1:分步骤实现 

实例讲解丨使用RxJava的最佳开发场景
方式2:基于事件流的链式调用


  • 具体使用

请看文章Android RxJava:面向初学者的RxJava使用指南

http://blog.csdn.net/carson_ho/article/details/79168602




3
实际开发应用场景



RxJava的实际开发应用场景 与 其对应的操作符息息相关


  • 常见的RxJava实际开发应用场景有如下:

实例讲解丨使用RxJava的最佳开发场景

下面实例皆结合常用框架如 Retrofit 、RxBinding、RxBus 



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


  • 需求场景 

实例讲解丨使用RxJava的最佳开发场景

  • 具体实现 


Android RxJava 实际应用讲解:(无条件)网络请求轮询

https://www.jianshu.com/p/11b3ec672812



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


  • 需求场景 

实例讲解丨使用RxJava的最佳开发场景

  • 具体实现 


Android RxJava 实际应用讲解:(有条件)网络请求轮询

http://blog.csdn.net/carson_ho/article/details/78256466



3.3 网络请求出错重连


  • 需求场景 

实例讲解丨使用RxJava的最佳开发场景

  • 功能需求说明

实例讲解丨使用RxJava的最佳开发场景

  • 功能逻辑

实例讲解丨使用RxJava的最佳开发场景

  • 具体实现 


Android RxJava 实际应用讲解:网络请求出错重连(结合Retrofit)

http://blog.csdn.net/carson_ho/article/details/78651602



3.4 网络请求嵌套回调


  • 背景 


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


  • 冲突 


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


// 发送注册网络请求的函数方法
   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();
                   }
               });
   }


  • 解决方案 


结合 RxJava2中的变换操作符FlatMap()实现嵌套网络请求


  • 具体实现 


Android RxJava 实际应用讲解:网络请求嵌套回调

http://blog.csdn.net/carson_ho/article/details/78315696



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


  • 需求场景 

实例讲解丨使用RxJava的最佳开发场景

  • 功能说明 


对于从磁盘 / 内存缓存中 获取缓存数据 的功能逻辑如下: 

实例讲解丨使用RxJava的最佳开发场景

  • 具体实现 


Android RxJava 实际应用讲解:从磁盘 / 内存缓存中 获取缓存数据

http://blog.csdn.net/carson_ho/article/details/78455449


3.6 合并数据源


  • 需求场景

实例讲解丨使用RxJava的最佳开发场景

  • 功能说明 


即,同时向2个数据源获取数据 -> 合并数据 -> 统一展示到客户端


  • 具体实现 


Android RxJava 实际应用讲解:合并数据源

http://blog.csdn.net/carson_ho/article/details/78455544



3.7 联合判断


  • 需求场景 


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


  • 功能说明 


此处采用 填写表单 作为联合判断功能展示,即,表单里所有信息(姓名、年龄、职业等)都被填写后,才允许点击 “提交” 按钮


  • 具体实现 


Android RxJava 实际应用讲解:联合判断

http://blog.csdn.net/carson_ho/article/details/78455624



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


  • 需求场景 


即,新开工作线程执行耗时操作;待执行完毕后,切换到主线程实时更新 UI


  • 具体实现 


Android RxJava:细说 线程控制(切换 / 调度 )(含Retrofit实例讲解)

https://www.jianshu.com/p/5225b2baaecd



3.9 功能防抖


  • 需求场景

实例讲解丨使用RxJava的最佳开发场景

  • 功能说明

实例讲解丨使用RxJava的最佳开发场景

  • 具体实现 


Android RxJava 实际应用讲解:功能防抖

http://blog.csdn.net/carson_ho/article/details/78849689



3.10 联想搜索优化


  • 需求场景 

实例讲解丨使用RxJava的最佳开发场景

  • 功能说明

实例讲解丨使用RxJava的最佳开发场景

  • 具体实现 


Android RxJava 实际应用讲解:联想搜索优化

http://blog.csdn.net/carson_ho/article/details/78849661



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


a. 背景


观察者 & 被观察者 之间存在2种订阅关系:同步 & 异步。具体如下:

实例讲解丨使用RxJava的最佳开发场景

对于 异步订阅 关系,存在 被观察者发送事件速度 与观察者接收事件速度 不匹配的情况 


  1. 发送 & 接收事件速度 = 单位时间内 发送&接收事件的数量 

  2. 大多数情况,主要是 被观察者发送事件速度 > 观察者接收事件速度



b. 冲突 


观察者无法及时响应 / 处理所有发送过来事件的问题,最终导致缓存区溢出、事件丢失 & OOM


举个例子:


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

  • 观察者的接收事件速度 = 5s / 个


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

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. 解决方案 


采用 背压策略


  • 具体实现 


Android :全面解析RxJava 背压策http://blog.csdn.net/carson_ho/article/details/79081407




4
总结



以上是关于实例讲解丨使用RxJava的最佳开发场景的主要内容,如果未能解决你的问题,请参考以下文章

Android RxJava:你必须了解的线程控制(含实例讲解)

Carson带你学Android:RxJava线程控制(含实例讲解)

最佳实践丨云开发CloudBase内容审核能力

精通高级RxJava 2响应式编程思想

最适合使用RxJava处理的四种场景

最佳实践丨云开发CloudBase多环境管理实践