当我触发此代码时:
timer(1000).pipe(
expand(() => of('a')),
take(3)
)
.subscribe(data => alert(data));
我收到3次警报:警报为0,警报为“ a”,警报为“ a”。 我只想通过数组[0,a,a]收到一个警报。 如何合并所有值?
答案 0 :(得分:2)
您的问题很有趣,并且(如Michael D在其回答中所述)非常具体的用例。
An example of the following code, working in StackBlitz
我建议您使用reduce,而不是使用scan
(这将为您提供3种排放量中每个排放量上的当前累积值),webchat只会在来源完成。
import { of, timer } from 'rxjs';
import { reduce, expand, take } from 'rxjs/operators';
timer(1000).pipe(
expand(() => of('a')),
take(3),
reduce((acc, val) => { acc.push(val); return acc; }, [])
).subscribe(val => console.log('Output:', val));
//输出:[0,a,a]
答案 1 :(得分:1)
这看起来是一个非常具体的用例,并且有多种实现方法。
scan
和filter
运算符timer(1000).pipe(
expand(() => of('a')),
take(3),
scan((acc, curr) => {
acc.push(curr); // <-- push each notification to the array
return acc;
}, []), // <-- empty array `[]` as seed value
filter(values => values.length === 3) // <-- emit only if notification length is 3
).subscribe(data => alert(data));
请注意,使用scan
的可观察符正在发出3条通知:[0]
,[0, 'a']
和[0, 'a', 'a']
。我们明确限制仅发出最后一个通知,因为我们知道它的长度应为3(由于take(3)
)。
scan
和takeLast
运算符timer(1000).pipe(
expand(() => of('a')),
take(3),
scan((acc, curr) => {
acc.push(curr); // <-- push each notification to the array
return acc;
}, []), // <-- empty array `[]` as seed value
takeLast(1) // <-- emit the last 1 notification
).subscribe(data => alert(data));
scan
和last
运算符timer(1000).pipe(
expand(() => of('a')),
take(3),
scan((acc, curr) => {
acc.push(curr); // <-- push each notification to the array
return acc;
}, []), // <-- empty array `[]` as seed value
last() // <-- emit the last notification
).subscribe(data => alert(data));
last
运算符还提供了一个类似于filter
运算符的选项。您可以传递谓词,并且仅在满足谓词的情况下才会发出通知。
timer(1000).pipe(
expand(() => of('a')),
take(3),
scan((acc, curr) => {
acc.push(curr); // <-- push each notification to the array
return acc;
}, []), // <-- empty array `[]` as seed value
last((values) => values.includes('a')) // <-- emit only if array contains 'a'
).subscribe(data => alert(data));
reduce
运算符请参阅@NathanBeck的answer。
toArray
运算符可能最快的解决方案是使用toArray()
运算符。
timer(1000).pipe(
expand(() => of('a')),
take(3),
toArray()
).subscribe(data => alert(data));