首页 > 解决方案 > 保证发射之间的“n”秒,而无需最初等待

问题描述

给定一个事件流,例如 (each -is 10ms)

--A-B--C-D

debounceTime(20)我们得到

-----------D

throttleTime(20)我们得到

--A----C--

throttleTime(20, undefined, {leading: true, trailing: true}我们得到

--A----CD

相反,我如何保证每次发射之间有那么多时间,例如20ms

--A-----C--D

一般来说,throttleTime最接近的trailing: true,但有时会导致trailing输出太接近leading输出。

示例代码可以在rxviz.com上找到

标签: rxjs

解决方案


1.连接延迟

将空延迟连接到每个项目,它不会发出任何内容,并且仅在给定时间后完成。

const { EMTPY, of, concat } = Rx;
const { concatMap, delay } = RxOperators;

event$.pipe(
  concatMap(item => concat(of(item), EMPTY.pipe(delay(20))))
);

在此处输入图像描述

2. ConcatMap 到定时器

将每个项目映射到从给定项目开始并在给定时间后完成的计时器。计时器完成时将发出下一个项目。计时器本身发出的值将被忽略。

const { timer } = Rx;
const { concatMap, ignoreElements, startWith } = RxOperators;

event$.pipe(
  concatMap(item => timer(20).pipe(ignoreElements(), startWith(item)))
);

3. 间隔压缩(不是最优的)

如果您的事件流发出的项目比所需的延迟更快,您可以zip在间隔发出时发出事件。

const { interval, zip } = Rx;
const { map } = RxOperators;

zip(event$, interval(20)).pipe(map(([item, i]) => item));

此方法不能保证n在所有情况下每个发射项目之间的秒数,例如,当间隔大于所需延迟时,事件流中有一个小间隔。

例如zip,在您的示例中,在 20、30、50、60 处发射,最小延迟为 20。
zip在 20、30、65、70 处发射,最小延迟为 20 时,将无法完美工作。

interval发出的速度快于事件的进入速度时,那些间隔项目将堆积在zip. 如果是这种情况,zip将立即从堆栈中压缩任何具有已存在间隔项的新事件,从而导致事件在没有预期延迟的情况下发出。


推荐阅读