Rxjs中有三种操做符都是用做从主流转换到从流上的,它们分别是switchMap
、concatMap
、flatMap
和exhaustMap
。RxViz能够将流进行可视化,咱们就利用RxViz来一探这四种操做符的异同。缓存
整体上来讲,四个操做符的做用都是:存在一个主流和一个从流,主流上每发射一次数据都会触发从流开始发射数据,最后数据都被打平到同一个输出流中,以下图所示。spa
如下四个例子,主流是每500毫秒发射一次数据,从流是每200毫秒发射数据,每次主流发射数据都会触发从流。code
var mainstream = Rx.Observable.interval(500); mainstream.switchMap((x) => Rx.Observable.interval(200).take(5));
从结果能够看到,用switchMap
的时候,从流每次只能发射2个数据0-1,这是由于主流每发射一次触发了从流的发射,可是在从流发射的过程当中,若是主流又一次发射了数据,switchMap
会截断上一次的从流,响应本次的主流,从而开启新的一段的从流发射。blog
var mainstream= Rx.Observable.interval(500); mainstream.concatMap((x) => Rx.Observable.interval(200).take(5));
从结果能够看到,用concatMap
的时候,虽然在从流尚未结束的时候,主流还在发射数据,主流会先把发射的数据缓存起来,等从流结束后当即响应主流的数据从而引起新一轮的从流发射,这有些相似与js
的消息队列机制。因此咱们看到它的输出流响应是连续的。队列
代码:图片
var mainstream= Rx.Observable.interval(500); mainstream.flatMap((x) => Rx.Observable.interval(200).take(5));
分析:
从结果能够看出来,flatMap
/mergeMap
会即便响应主流中发射的每个数据,它既不会忽略也不会缓存,这就致使主流中数据对应的从流产生了叠加。ip
var mainstream= Rx.Observable.interval(500); mainstream.exhaustMap((x) => Rx.Observable.interval(200).take(5));
从结果能够看出,exhaustMap
在从流尚未结束的时候若是主流仍然有数据在发射,它会忽略此时主流发射的数据,而在从流结束之后才会去响应主流中发射的数据。get