Rxjs 响应式编程和异步编程(一)
在Angular中,内置了很多可观察(Observable)对象,这些对象具有可订阅性,当有消费者调用subscribe()方法时,这个函数就执行,普遍用于前端请求处理的场景。本篇暂时脱离Angular,集中到rxjs本身的api操作符上,挑选最常见的操作符作为demo。
操作符
按照类型划分为 组合
、条件
、创建
、错误处理
、过滤
、多播
、转换
、工具
创建一个 Observable
create
import { Observable,from } from 'rxjs'; const content = Observable.create((observer)=>{ observer.next('something'); });
from
import { Observable,from } from 'rxjs'; const source = from([1,2,3,4]);
fromEvent
将事件转成 Observable 序列
import { fromEvent } from 'rxjs'; const source = fromEvent(document, 'click'); source.subscribe(val => { console.log(val); })
of
按顺序发出任意数量的值
import { of } from 'rxjs'; const source = of(1,2,3,4);
其他:empty
立即完成
const subscribe = empty().subscribe({ next:()=>console.log('next'), complete:()=>console.log('complete') });
interval
基于给定时间间隔发出数字序列
source.subscribe(res=>{ console.log(res); });
timer
给定一定的时间后,根据第二参数时间间隔发出值,缺失第二参数,则只发出一次值
const source = timer(1000,500); source.subscribe(res=>{ console.log(res); });
过滤操作
filter
类似数组的操作api,挑选符合条件的进行返回
比如从一组返回的数据中筛选符合的样本,原本的做法是订阅者将数据全部获取进行筛选,这份工作可以转移到filter操作中进行,订阅者拿到的就是符合预期的数据。
const source = from([1, 2, 3, 4, 5, 6]).pipe(filter((o: number) => o > 3)); source.subscribe(res=>{ console.log(res); });
take
在完成前指定发出N个值
如:首次点击有效
const oneClickEvent = fromEvent(document, 'click') .pipe( take(1) ); oneClickEvent.subscribe(event => { console.log(event); });
转换(核心)
map
对每个源observable的每个值应用投射函数(加工处理,格式转换、补全等)
const source = from(['abc', 'DEf', 'cDt']).pipe( map((o: any) => o.toLocaleLowerCase() ) ); source.subscribe(res=>{ console.log(res); });
switchMap
和其他打平操作符的主要区别是它具有取消效果。在每次发出时,会取消前一个内部 observable (你所提供函数的结果) 的订阅,然后订阅一个新的 observable 。你可以通过短语切换成一个新的 observable来记忆它。
应用:拦截后处理,取消之前发出但还未结束的订阅操作。
模拟两个按钮发起可订阅的操作(如http请求)
const mapBtn = window.document.getElementsByClassName('btn'); const switchMapBtn = window.document.getElementsByClassName('switchMap'); const interval$ = interval(1000); let mapClickCount = 0; let switchMapCount = 0; const source = fromEvent(mapBtn, 'click') .pipe( map(event => { mapClickCount++; return interval$; }), ); source.subscribe((observal) => { observal.subscribe(res => { console.log(`map clickCounts: ${mapClickCount},and res is ${res}`); }) }); const switchMapSource = fromEvent(switchMapBtn, 'click') .pipe( switchMap(event => { switchMapCount++; return interval$; }), ); switchMapSource.subscribe(res => { console.log(`switchMap clickCounts: ${switchMapCount},and res is ${res}`); })
点击第一个普通订阅按钮2次(间隔1s):
对比使用switchMap的按钮:
图2中每次按钮点击都会取消之前的订阅数值,重新计算。
工具
toPromise
将 obeservable转换成promise。
const source = from([1, 2, 3]); const promise: Promise<any>[] = []; source.pipe( map(o => { return of(o).toPromise() }) ).subscribe(res => { promise.push(res); }); Promise.all(promise).then(res=>{ console.log(res); //[1,2,3] });
delay
延迟时间
const source = from([1, 2, 3]); source.pipe( map(o => { console.log(new Date().getSeconds()); return o; }), delay(5000) ).subscribe(res=>{ console.log(`${new Date().getSeconds()} ${res}`); });
tap
5.5v以前的do操作符重命名,使用场景:输出执行日志等
const source = from([1, 2, 3]); source.pipe( tap(o => console.log(o)), map(o => { return o; }), ).subscribe(res => { console.log(`${res}`); });
Rxjs学习网址:https://cn.rx.js.org/class/es6/Observable.js~Observable.html
翻译网站:
https://rxjs-cn.github.io/learn-rxjs-operators/
原文地址:https://segmentfault.com/a/1190000021143815
相关推荐
-
Jquery会死吗?我为什么不用vue写富文本! javascript/jquery
2019-5-13
-
面试官问你基本类型时他想知道什么 javascript/jquery
2019-4-14
-
探讨奇技淫巧 javascript/jquery
2019-6-7
-
typescript—mixins javascript/jquery
2020-5-24
-
再也不想写表单了 javascript/jquery
2019-3-6
-
循序渐进VUE+Element 前端应用开发(8)— 树列表组件的使用,循序渐进VUE+Element 前端应用开发(5)— 表格列表页面的查询,列表展示和字段转义处理, javascript/jquery
2020-7-11
-
15 个有趣的 JavaScript 与 CSS 库 javascript/jquery
2020-6-9
-
要如何在Viewer本地模式下使用加载 AEC Model Data? javascript/jquery
2020-5-27
-
如何优雅地处理Async/Await的异常? javascript/jquery
2019-8-6
-
【javascript】函数中的this的四种绑定形式 — 大家准备好瓜子,我要讲故事啦~~ javascript/jquery
2019-8-17