简单模拟实现Rxjs Observable
1.先定义类型
export type Observer = { next: (any) => void, complete?: (any) => void, } export interface OnSubscribeAction { (observer: Observer): void; }
export interface mapFun {
(x: any): any
}
2.自定义类
export class MyObservable { private subscribeAction: OnSubscribeAction; constructor(subscribeAction: OnSubscribeAction) { this.subscribeAction = subscribeAction; } subscribe(observer: Observer) { return this.subscribeAction(observer) } }
3.实例
const onSubscribe: OnSubscribeAction = (observer: Observer) => { observer.next(1); observer.next(2); observer.next(3); } const theObserver = { next: console.log, } const source$ = new MyObservable(onSubscribe); source$.subscribe(theObserver);
结果一次输出1,2,3
4.增加map操作符
export class MyObservable { private subscribeAction: OnSubscribeAction; constructor(subscribeAction: OnSubscribeAction) { this.subscribeAction = subscribeAction; } subscribe(observer: Observer) { return this.subscribeAction(observer) } //rxjs 的每个操作符都会返回一个新的Observable map(fun: mapFun) { const nextObserver = new MyObservable((observer: Observer) => { this.subscribe({ next(item){ observer.next(fun(item)) } }) }) return nextObserver } }
5.再次调用
const onSubscribe: OnSubscribeAction = (observer: Observer) => { observer.next(1); observer.next(2); observer.next(3); } const theObserver = { next: console.log, } const source$ = MyObservable.create(onSubscribe); source$.map(x => x * 2).map(x => x + 1).subscribe(theObserver);
结果一次输出3,5,7
=====================================
更进一步把map作为一个单独的函数抽离
export function map(fun: mapFun) { const nextObserver = new MyObserver((observer: Observer) => { this.subscribe({ next(item){ observer.next(fun(item)) } }) }) return nextObserver }
完整代码如下所示
export type Observer = { next: (any) => void, complete?: (any) => void, } export interface OnSubscribeAction { (observer: Observer): void; } export interface mapFun { (x: any): any } export function map(fun: mapFun) { const nextObserver = new MyObservable((observer: Observer) => { this.subscribe({ next(item){ observer.next(fun(item)) } }) }) return nextObserver } export class MyObservable { private subscribeAction: OnSubscribeAction; constructor(subscribeAction: OnSubscribeAction) { this.subscribeAction = subscribeAction; } static create(subscribeAction: OnSubscribeAction) { return new MyObservable(subscribeAction) } subscribe(observer: Observer) { return this.subscribeAction(observer) } }
由于map函数中使用到this,需要用call或者apply或者bind改变其指向,使用示例如下
const onSubscribe: OnSubscribeAction = (observer: Observer) => { observer.next(1); observer.next(2); observer.next(3); } const theObserver = { next: console.log, } const source$ = new MyObservable(onSubscribe); const subScribtion$ = map.call(source$, x => x * 2); map.call(subScribtion$, x => x + 1).subscribe(theObserver);
输出结果依次为3,5,7
=====================
由于在map函数中需要访问this, 导致map不是一个纯函数。在map中的this指代上一个observable,现在改为通过参数传递的形式把上一个observable传递给下一个observable。
map函数修改如下
export function map(fun: mapFun) { return function(obs$) { const nextObserver = new MyObservable((observer: Observer) => { obs$.subscribe({ next(item){ observer.next(fun(item)) } }) }) return nextObserver } }
同时MyObservable自定义类需要增加一个pipe方法
export class MyObservable { private subscribeAction: OnSubscribeAction; constructor(subscribeAction: OnSubscribeAction) { this.subscribeAction = subscribeAction; } subscribe(observer: Observer) { return this.subscribeAction(observer) } pipe(fn: any){ return fn(this); } }
最终的调用方式如下
const onSubscribe: OnSubscribeAction = (observer: Observer) => { observer.next(1); observer.next(2); observer.next(3); } const theObserver = { next: console.log, } const source$ = new MyObservable(onSubscribe); source$.pipe(map(x => x*2)).pipe(map(x => x + 1)).subscribe(theObserver)
结果依次输出3,5,7