头图

rxjs 里 CombineLatest 操作符的一个使用场景

一个具体的例子:

combineLatest([
  data$.pipe(startWith(null)),
  loading$,
]).pipe(
  takeWhile(([data, loading]) => !data || loading, true),
  map(([data, loading]) => loading ? null : data),
  skip(1),
  distinctUntilChanged(),
);

我们在这里使用巧妙的 takeWhile 函数。 它只会让带有虚假数据(falsy data)(初始 null )或 truthy loading 的发射值通过,这正是我们需要显示 spinner 的时候。 当条件不满足时,由于第二个参数,我们也让最终值通过。

然后我们使用 map 函数映射结果。 如果 loading 标志位为 true,则 map 返回的值为 null,这很合理,因为 loading 的时候是肯定没有数据返回的。当 loading 标志位为 false,说明数据返回完毕,则返回真实的 data.

我们使用 skip(1) 是因为我们不希望我们的 startWith(null) 数据流通过。 我们使用 distinctUntilChanged 所以多个空值也不会通过。

这里涉及到的知识点:

  1. startWith

一个例子:

// RxJS v6+
import { startWith } from 'rxjs/operators';
import { of } from 'rxjs';

//emit (1,2,3)
const source = of(1, 2, 3);
//start with 0
const example = source.pipe(startWith(0));
//output: 0,1,2,3
const subscribe = example.subscribe(val => console.log(val));

上面的 example 订阅后,会打印通过 startWith 传入的初始值 0,然后是 of 包裹的1,2,3

  1. takeWhile

这个 Operator 会持续发射数据,直接传入的条件不满足,则终止数据 emit.

注意 takeWhile 和 filter 的区别在于,前者在遇到 condition 为 false 时,会 fire 一个 complete 事件,而后者不会。

下面是一个具体的比较:

// RxJS v6+
import { of } from 'rxjs';
import { takeWhile, filter } from 'rxjs/operators';

// emit 3, 3, 3, 9, 1, 4, 5, 8, 96, 3, 66, 3, 3, 3
const source$ = of(3, 3, 3, 9, 1, 4, 5, 8, 96, 3, 66, 3, 3, 3);

// allow values until value from source equals 3, then complete
source$
  .pipe(takeWhile(it => it === 3))
  // log: 3, 3, 3
  .subscribe(val => console.log('takeWhile', val));

source$
  .pipe(filter(it => it === 3))
  // log: 3, 3, 3, 3, 3, 3, 3
  .subscribe(val => console.log('filter', val));

takeWhile 在遇到 of Observable 里第四个元素即 9 时,就会 fire complete 事件,因此 of Observable 余下的所有元素,再没有被 emit 的机会,而 filter 则不然,最后会打印 of Observable 里所有的元素 3.


Jerry Wang的SAP技术专栏
SAP成都研究院开发专家,SAP社区导师,SAP中国技术大使
873 声望
1.6k 粉丝
0 条评论
推荐阅读
SAP OData 开发实战教程:从入门到提高
本教程根据笔者在 SAP 研究院工作多年的实战经验,计划通过 300 篇以上的文章篇幅,深入介绍 SAP 三大主流的 OData 开发技术:

JerryWang_汪子熙阅读 117

封面图
从零搭建 Node.js 企业级 Web 服务器(零):静态服务
过去 5 年,我前后在菜鸟网络和蚂蚁金服做开发工作,一方面支撑业务团队开发各类业务系统,另一方面在自己的技术团队做基础技术建设。期间借着 Node.js 的锋芒做了不少 Web 系统,有的至今生气蓬勃、有的早已夭折...

乌柏木150阅读 12.3k评论 10

正则表达式实例
收集在业务中经常使用的正则表达式实例,方便以后进行查找,减少工作量。常用正则表达式实例1. 校验基本日期格式 {代码...} {代码...} 2. 校验密码强度密码的强度必须是包含大小写字母和数字的组合,不能使用特殊...

寒青56阅读 7.9k评论 11

JavaScript有用的代码片段和trick
平时工作过程中可以用到的实用代码集棉。判断对象否为空 {代码...} 浮点数取整 {代码...} 注意:前三种方法只适用于32个位整数,对于负数的处理上和Math.floor是不同的。 {代码...} 生成6位数字验证码 {代码...} ...

jenemy46阅读 6k评论 12

从零搭建 Node.js 企业级 Web 服务器(十五):总结与展望
总结截止到本章 “从零搭建 Node.js 企业级 Web 服务器” 主题共计 16 章内容就更新完毕了,回顾第零章曾写道:搭建一个 Node.js 企业级 Web 服务器并非难事,只是必须做好几个关键事项这几件必须做好的关键事项就...

乌柏木66阅读 6.2k评论 16

再也不学AJAX了!(二)使用AJAX ① XMLHttpRequest
「再也不学 AJAX 了」是一个以 AJAX 为主题的系列文章,希望读者通过阅读本系列文章,能够对 AJAX 技术有更加深入的认识和理解,从此能够再也不用专门学习 AJAX。本篇文章为该系列的第二篇,最近更新于 2023 年 1...

libinfs39阅读 6.3k评论 12

封面图
从零搭建 Node.js 企业级 Web 服务器(一):接口与分层
分层规范从本章起,正式进入企业级 Web 服务器核心内容。通常,一块完整的业务逻辑是由视图层、控制层、服务层、模型层共同定义与实现的,如下图:从上至下,抽象层次逐渐加深。从下至上,业务细节逐渐清晰。视图...

乌柏木44阅读 7.4k评论 6

873 声望
1.6k 粉丝
宣传栏