Function rxjs缓冲区,直到新arg到达时超时重置

Function rxjs缓冲区,直到新arg到达时超时重置,function,rxjs,accumulate,debounce,Function,Rxjs,Accumulate,Debounce,小结:我正在使用Rxjs和一个新手。我想实现这样一个场景,可以观察到,但到目前为止还没有运气 有一个函数loadDetailsFromServer(ItemId),它调用服务器api并传递一些ItemId。此函数偶尔调用。要优化服务器调用,我想做以下几点: 当第一个函数调用到达时,将触发超时。如果在超时之前任何新函数调用到达,timout将重置为重新启动。当超时开始时,进行服务器调用,参数计数重置为零 这是一张大理石般的图表: Timer is 4 clicks. INPUTS IN TIME

小结:我正在使用Rxjs和一个新手。我想实现这样一个场景,可以观察到,但到目前为止还没有运气

有一个函数loadDetailsFromServer(ItemId),它调用服务器api并传递一些ItemId。此函数偶尔调用。要优化服务器调用,我想做以下几点: 当第一个函数调用到达时,将触发超时。如果在超时之前任何新函数调用到达,timout将重置为重新启动。当超时开始时,进行服务器调用,参数计数重置为零

这是一张大理石般的图表:

Timer is 4 clicks.
INPUTS IN TIME        1-2---3-4-----5--------6-7--------
loadDetailsFromServer [1,2,3,4]   -      [5]         -[6,7]  

function called with [1,2,3,4] because no more calls after 4 clicks.

提示:这类似于搜索框示例并从服务器获取结果,不同之处在于中间值很重要,不会被忽略/跳过。

例如,如果您有如下可观察的源:

const Rx = require('rxjs/Rx');
const Observable = Rx.Observable;

const TIMEOUT = 1000;

const source = Observable.range(1, 20)
    .concatMap(v => Observable.of(v).delay(Math.random() * 2000));
然后可以使用
扫描
缓冲其值。要重置缓冲区,我正在使用
.merge(bufferNotifier.mapTo(null))
。然后使用
switchMap()
我总是等待1000毫秒,等待
forkJoin()
发出。如果没有,则会被另一个可观察对象“覆盖”,因为新缓冲区已到达:

const bufferNotifier = new Subject();

const chain = source
    .do(undefined, undefined, () => bufferNotifier.complete()) // properly complete the chain
    .merge(bufferNotifier.mapTo(null)) // reset buffer Subject
    .scan((acc, val) => {
        if (val === null) {
            return [];
        }
        acc.push(val);
        return acc;
    }, [])
    .filter(arr => arr.length > 0)
    .switchMap(buffer => { // wait 1s until emitting the buffer further
        return Observable.forkJoin(
            Observable.of(buffer),
            Observable.timer(1000).take(1),
            arr => arr
        );
    })
    .do(() => bufferNotifier.next()) // trigger reset the buffer
    .subscribe(console.log);
这将输出例如:

[ 1 ]
[ 2 ]
[ 3, 4 ]
[ 5 ]
[ 6, 7 ]
[ 8, 9, 10, 11, 12 ]
[ 13 ]
[ 14, 15 ]
[ 16 ]
[ 17 ]
[ 18 ]
[ 19, 20 ]

如果你有一个类似的
源代码
可以观察到martin的答案,类似的东西可能会起作用:

source
  .buffer(source.debounceTime(250))
  .subscribe(console.log);
buffer
收集所有发射值,直到给定的可观测发射。在这种情况下,它将等待
debounceTime
发出。代码笔: