0%

rxjs操作符:of和from

感觉of操作符在快速创建Observable的时候挺方便的,使用from在进行一些转化的,对这两个操作符进行整理一下。

操作符of

1
2
3
4
5
6
7
8
9
10
11
12
public static of(values: ...T, scheduler: Scheduler): Observable<T>
```
创建一个Observable,它会一次发出提供的参数,最后发出完成通知。

这个静态操作符用于创建简单的Observable,该Observable只发出给定的参数,在发送完这些参数后发出完成通知。它可以用来和其他的Observables组合比如说`concat`。默认情况下,使用`null`调度器,这意味着`next`通知是同步发出的,尽管使用不同的调度器可以决定这些通知何时送到。

例如:
``` js
of(1, 2, 3).subscribe(res => {
console.log(res);
});
// 控制台依次输出:1, 2, 3

可以使用concat和其他Observable组合,例如:

1
2
3
4
5
6
7
const ofListObs = of(1, 2, 3);
const strObs = of('a', 'b', 'c');
const intervalObs = interval(500);
const resObs = concat(ofListObs, strObs, intervalObs);
resObs.subscribe(res => {
console.log(res);
});

依次先发出1、2、3、a、b、c,然后一秒发出一个数字。

操作符 from

1
public static from(ish: ObservableInput<T>, scheduler: Scheduler): Observable<T>

从一个数组、类数组对象、promise、迭代器对象或者类Observable对象创建一个Observable。

几乎可以把任何东西都能转化为Observable。

将数组转化为Observable

从一般数组转化:

1
2
3
4
from([1, 2, 3]).subscribe(res => {
console.log(res);
});
// 输出1, 2, 3

将Observable转化为Observable:

1
2
3
4
5
6
 from([of(1, 2, 3), of('a', 'b', 'c')]).pipe(
concatAll(),
).subscribe(res => {
console.log(res);
});
// 依次输出:1, 2, 3,a, b, c

将字符串转化为Observable

1
2
3
4
from('test').subscribe(res => {
console.log(res);
});
// 依次输出test

将一个无限迭代器转化为Observable

创建一个无限迭代器:

1
2
3
4
5
6
7
 static * generateDoubles(seed) {
let i = seed;
while (true) {
yield i;
i = 2 * i;
}
}

通过from转化迭代器为Observable(只取迭代器的前十个):

1
2
3
4
5
6
7
const iterator = OfFromComponent.generateDoubles(3);
from(iterator).pipe(
take(10),
).subscribe(res => {
console.log(res);
});
// 依次输出 3 6 12 24 48 96 192 384 768 1536

从promise转化

1
2
3
from(new Promise(resolve => resolve('hello'))).subscribe(res => {
console.log(res);
});

从集合中转化

1
2
3
4
5
6
7
const m = new Map();
m.set({a: '3'}, 'hi');
m.set({b: 4}, 'tony');
from(m).subscribe(res => {
console.log(res);
});
// 依次输出:[{"a":"3"},"hi"], [{"b":4},"tony"]

扩展:fromPromise、fromEvent、fromEventPattern

除了通用的from操作符,还有fromPromise专门处理Promise转换Observable,以及fromEvent专门处理事件转换Observable。

fromPromise

1
public static fromPromise(promise: PromiseLike<T>, scheduler: Scheduler): Observable<T>

将promise转化为Observable.

返回一个仅仅发出Promise resolve过的值然后完成的Observable。

如果Promise resolve一个值,输出Observable发出这个值然后完成。如果Promise被rejected,输出Observable后发生相应的错误。

1
2
3
4
5
6
7
8
9
10
11
12
fromPromise(fetch('http://www.mxnzp.com/api/weather/current/%E6%B7%B1%E5%9C%B3')).subscribe(
res => {
if (res.status === 200) {
res.json().then(r => {
console.log(r);
});
}
},
err => {
console.log('err', err);
}
);

fetch方法比较特殊,返回一个Promise,然后json()后继续Promise.then()才可以拿到接口的返回值。

fromEvent

1
public static fromEvent(target: EventTargetLike, eventName: string, options: EventListenerOptions, selector: SelectorMethodSignature<T>): Observable<T>

创建一个Observable,该Observable发出来自给定事件对象的指定类型事件。

创建一个来自于DOM事件,或者Node的EventEmitter事件或其他事件的Observable。

通过给“事件目标”添加时间监听器的方式创建Observable,可能会是拥有addEventListenerremoveEventListener方法的对象,一个Node.js的EventEmitter,一个jQuery式的EventEmitter,一个Dom的节点集合,或者Dom的HTMLCollection。Observable被订阅的时候事件处理函数会被添加,当取消订阅的时候会将事件处理函数移除。

名称 类型 属性 描述
target EventTargetLike 必须 事件目标,事件处理的对象
eventName string 必填 事件名称,从target发出
options EventListenerOptions 可选 传递给addEventListener的参数
selector SelectorMethodSignature 可选 函数处理的结果
1
2
3
4
fromEvent(document, 'click').subscribe(x => {
console.log('click', x);
});
// 发出dom document上的点击事件,每次点击时,都会在控制台发出 MouseEvent

对上面的程序进行扩展,点击页面上的任何地方,出现一个小东西,0.5s后消失:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
constructor(
private render: Renderer2,
private el: ElementRef,
) {
}
fromEvent(document, 'click').subscribe((event: MouseEvent) => {
// 获得坐标
const x = event.clientX;
const y = event.clientY;

const devDom = this.render.createElement('div');
devDom.className = 'lover';
this.render.setStyle(devDom, 'top', y + 'px');
this.render.setStyle(devDom, 'left', x + 'px');
this.render.appendChild(this.el.nativeElement, devDom);
// 500毫秒后删除dom
timer(500).subscribe( num => {
this.render.removeChild(this.el.nativeElement, devDom);
});
});

fromEventPattern

一个从基于addHandler/removeHandler方法的api创建Observable。目前感觉没什么用,先占个坑,后面用到了再细化。


整理了of操作符和from操作符的用法,以及相关的fromEventfromPromise操作符。

码字辛苦,打赏个咖啡☕️可好?💘