异步编程入门之RxJs(一)
# 一、前言
# 1.1 Promise缺点
Promise的特点是无论有没有人关心它的执行结果,它都会立即开始执行,并且你没有机会取消这次执行。显然,在某些情况下这么做是浪费的甚至错误的- 以电商为例,如果某商户的订单不允许取消,你还会去买吗?
- 如果你发起了一个
Ajax请求,然后用户导航到了另一个路由,显然,你这个请求如果还没有完成就应该被取消,而不应该发出去 - 使用
Promise,你做不到,不是因为实现方面的原因,而是因为它在概念层(接口定义上)就无法支持取消 - 由于
Promise只会承载一个值,因此当我们要处理的是一个集合的时候就比较困难了。比如对于一个随机数列(总数未知),如果我们要借助Web API检查每个数字的有效性,然后对前一百个有效数字进行求和,那么用Promise写就比较麻烦了
# 1.2 Observable
- 它就是可观察对象,
Observable顾名思义就是可以被别人观察的对象,当它变化时,观察者就可以得到通知。换句话说,它负责生产数据,别人可以消费它生产的数据 Observable就像个传送带。这个传送带不断运行,围绕这个传送带建立了一条生产线,包括一系列工序,不同的工序承担单一而确定的职责。每个工位上有一个工人- 整个传送带的起点是原料箱,原料箱中的原料不断被放到传送带上。工人只需要待在自己的工位上,对面前的原料进行加工,然后放回传送带上或放到另一条传送带上即可,简单、高效、无意外
# 1.3 ReactiveX宝石图

- 中间的带箭头的线就像传送带,用来表示数据序列,这个数据序列被称为“流”。上方的流叫做输入流,下方的流叫做输出流。输入流可能有多个,但是输出流只会有一个(不过,流中的每个数据项也可以是别的流)
- 数据序列上的每个圆圈表示一个数据项,圆圈的位置表示数据出现的先后顺序,但是一般不会表示精确的时间比例,比如在一毫秒内接连出现的两个数据之间仍然会有较大的距离。只有少数涉及到时间的操作,其宝石图才会表现出精确的时间比例
- 圆圈的最后,通常会有一条竖线或者一个叉号。竖线表示这个流正常终止了,也就是说不会再有更多的数据提供出来了。而叉号表示这个流抛出错误导致异常中止了。还有一种流,既没有竖线也没有叉号,这种叫做无尽流,比如一个由所有自然数组成的流就不会主动终止。但是要注意,无尽流仍然是可以处理的,因为需要多少项是由消费者决定的。你可以把这个“智能”传送带理解为由下一个工位“叫号”的,没“叫号”下一项数据就不会过来
- 中间的大方框表示一个操作,也就是 operator —— 一个函数,比如这个图中的操作就是把输入流中的条目乘以十后放入输出流中。
- 看懂了宝石图,就能很形象的理解各种操作符了
# 二、Rxjs介绍
# 2.1 介绍
RxJS是ReactiveX编程理念的JavaScript版本。ReactiveX来自微软,它是一种针对异步数据 流的编程。简单来说,它将一切数据,包括HTTP请求,DOM事件或者普通数据等包装成流的形式,然后用强大丰富的操作符对流进行处理,使你能以同步编程的方式处理异步数据,并组合不同的操作符来轻松优雅的实现你所需要的功能RxJS是一种针对异步数据流编程工具,或者叫响应式扩展编程;可不管如何解释RxJS其目 标就是异步编程,Angular引入RxJS为了就是让异步可控、更简单。
目前常见的异步编程的几种方法:
- 回调函数
- 事件监听/发布订阅
PromiseRxjs
# 2.2 Promise和RxJS处理异步对比
// promise异步处理
// Promise 处理异步
getPromiseData() {
return new Promise(resolve = >{
setTimeout(() = >{
resolve('---promise timeout---');
},
2000);
});
// 使用
getPromiseData().then(d=>console.log(d))
@前端进阶之旅: 代码已经复制到剪贴板
// RxJS 处理异步:
getRxjsData() {
return new Observable(observer = >{
setTimeout(() = >{
observer.next('observable timeout');
},
2000);
});
}
// 使用