如何在 RxJS 中做不同的节流

How to do distinct throttle in RxJS

我花了几天时间,但找不到在 RxJS 中执行 "distinct throttle" 的方法。

假设每个事件在 4 个破折号内完成,"distinct throttle" 将执行如下:

-①-②-①--------①-----|->

[明显油门]

-①-②------------①-----|->

如何使用现有的 RxJS 运算符构建 "distinct throttle"?

您可以使用 groupBy 按值分隔通知,然后可以应用 throttleTime,然后可以使用 mergeMap 合并分组的可观察对象。像这样:

const { Subject } = rxjs;
const { groupBy, mergeMap, throttleTime } = rxjs.operators;

const source = new Subject();
const result = source.pipe(
  groupBy(value => value),
  mergeMap(grouped => grouped.pipe(
    throttleTime(400)
  ))
);

result.subscribe(value => console.log(value));

setTimeout(() => source.next(1), 100);
setTimeout(() => source.next(2), 300);
setTimeout(() => source.next(1), 400);
setTimeout(() => source.next(1), 900);
.as-console-wrapper { max-height: 100% !important; top: 0; }
<script src="https://unpkg.com/rxjs@6/bundles/rxjs.umd.min.js"></script>

distinctthrottle 在物品选择方面有 2 个不同的特征。 distinct 将选择第一项,而 throttle 将选择最后一项。

有时您想保持 throttle 的行为。

假设流是:chat-message-edit 事件 携带更新的文本。用户可以在节流期内多次编辑特定消息。
您希望确保始终保留每条消息的最新版本(在不同消息的编辑流中)。

我会遵循的一个可能的解决方案是 the one below

const source$ = from([
{id:1,content:"1a"}, 
{id:1,content:"1b"}, 
{id:1,content:"1c"}, 
{id:2,content:"2a"}, 
{id:2,content:"2b"}, 
{id:3,content:"3a"},
{id:3,content:"3b"},
{id:1,content:"1d"},
{id:1,content:"1e"},
{id:4,content:"4a"},
{id:4,content:"4b"},
{id:4,content:"4c"},
{id:4,content:"4e"},
{id:4,content:"4f"},
{id:3,content:"3c"},
{id:3,content:"3d"},
{id:3,content:"3e"}
]).pipe(concatMap((el)=> of(el).pipe(delay(500)) ));



const distinctThrottle = (throttleTime, keySelector)=>
    pipe(bufferTime(throttleTime),
          concatMap((arr)=>from(arr.reverse()).pipe(distinct(keySelector))  
        )) ;


let throttledStream = source$.pipe(distinctThrottle(1550, ({id})=>id));

throttledStream.subscribe(console.log);