Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/typescript/8.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Typescript 使用rxjs运算符在订阅上延迟后输出_Typescript_Rxjs_Operators_Delay - Fatal编程技术网

Typescript 使用rxjs运算符在订阅上延迟后输出

Typescript 使用rxjs运算符在订阅上延迟后输出,typescript,rxjs,operators,delay,Typescript,Rxjs,Operators,Delay,我需要获得如下输出: computing 1 5 6 7 8 wait 2 seconds computing 2 5 6 7 8 wait 2 seconds ... 但是使用以下代码 from([1,2,3,4]).pipe( concatMap(n => of(n).pipe( tap(n => {console.log(`computing ${n}`)}), concatMap(n => from([5,6,7,8]))

我需要获得如下输出:

computing 1
5
6
7
8

wait 2 seconds

computing 2
5
6
7
8

wait 2 seconds
...
但是使用以下代码

from([1,2,3,4]).pipe(
    concatMap(n => of(n).pipe(
        tap(n => {console.log(`computing ${n}`)}),
        concatMap(n => from([5,6,7,8])),
        delay(2000)
    ))
).subscribe((val) => {console.log(val)}, () => {}, () => {console.log(`end`)})
输出将是

computing 1

wait 2 seconds

5
6
7
8
computing 2

wait 2 seconds

5
6
7
8
computing 3

因为延迟将在最里面的展平后生效,并导致下一个计算x字符串在值之后立即打印。相反,我需要在不获得初始延迟的情况下获得上述示例输出,这可能吗?

首先,我们设置一个函数,创建一个开放一段时间的可观察对象,然后完成

const nothingFor=ms=>timerms.pipeconcatMapToEMPTY; 然后我们使用它来生成一个新的操作符,它的行为类似于delay*,但在之后应用延迟

const appendDelay=delay=>source$=> 对于Source$,nothingFordelay.pipeconcatal; 然后我们把它放在你最初使用延迟的地方

从[1,2,3,4] 管 concatMapn=> 水管 tapn=>{ log`computing${n}`; }, concatMapn=>from[5,6,7,8]。pipeappendDelay2000
*嗯,有点。延迟延迟相同数量的每次发射。如果这更像延迟,它将在每次发射后而不是在源完成后添加延迟。

首先,我们设置一个函数,创建一个开放一段时间的可观察对象,然后完成

const nothingFor=ms=>timerms.pipeconcatMapToEMPTY; 然后我们使用它来生成一个新的操作符,它的行为类似于delay*,但在之后应用延迟

const appendDelay=delay=>source$=> 对于Source$,nothingFordelay.pipeconcatal; 然后我们把它放在你最初使用延迟的地方

从[1,2,3,4] 管 concatMapn=> 水管 tapn=>{ log`computing${n}`; }, concatMapn=>from[5,6,7,8]。pipeappendDelay2000
*嗯,有点。延迟延迟相同数量的每次发射。如果这更像延迟,它将在每次发射后而不是在源完成后增加延迟。

这个问题的关键是,我们只想在第一个可观测源的第一次发射后引入延迟

我们可以将concatMap与delayWhen操作符结合使用,让我们选择条件延迟。条件延迟可以建立在第一个可观察到的迭代的索引之上。如果索引为0,则没有延迟,否则有2秒延迟

在第一个可观察和后条件延迟中的每个项目发射之后,我们使用switchMap切换到第二个可观察流,这将帮助我们获得所需的输出

import { from, iif, interval, of } from "rxjs";
import { concatMap, delayWhen, map, switchMap, tap } from "rxjs/operators";

const a$ = from([1, 2, 3, 4]);
const b$ = from([5, 6, 7, 8]);

const conditionalDelay$ = index => y =>
  iif(() => index === 0, interval(0), interval(2000));

const logDelay = index => () => {
  if (index !== 0) console.log("Wait for 2 seconds");
};

const result$ = a$.pipe(
  concatMap((x, index) =>
    of(x).pipe(
      tap(logDelay(index)),
      delayWhen(conditionalDelay$(index))
    )
  ),
  switchMap(x => {
    console.log("Computing", x);
    return b$.pipe(map(y => console.log(y)));
  })
);

result$.subscribe(x => console.log(x));

这个问题的关键是,我们只想在第一个可观测源的第一次发射之后引入延迟

我们可以将concatMap与delayWhen操作符结合使用,让我们选择条件延迟。条件延迟可以建立在第一个可观察到的迭代的索引之上。如果索引为0,则没有延迟,否则有2秒延迟

在第一个可观察和后条件延迟中的每个项目发射之后,我们使用switchMap切换到第二个可观察流,这将帮助我们获得所需的输出

import { from, iif, interval, of } from "rxjs";
import { concatMap, delayWhen, map, switchMap, tap } from "rxjs/operators";

const a$ = from([1, 2, 3, 4]);
const b$ = from([5, 6, 7, 8]);

const conditionalDelay$ = index => y =>
  iif(() => index === 0, interval(0), interval(2000));

const logDelay = index => () => {
  if (index !== 0) console.log("Wait for 2 seconds");
};

const result$ = a$.pipe(
  concatMap((x, index) =>
    of(x).pipe(
      tap(logDelay(index)),
      delayWhen(conditionalDelay$(index))
    )
  ),
  switchMap(x => {
    console.log("Computing", x);
    return b$.pipe(map(y => console.log(y)));
  })
);

result$.subscribe(x => console.log(x));

对您的代码进行一个小小的调整,就可以让它按照您想要的方式工作。与简单地返回concatMap中的所需可观测值不同,您可以返回一个可观测值,第一个可观测值发出所需可观测值,然后是一个不发出任何信息的可观测值,然后在延迟后完成

为此,我们可以使用和:

来自[1,2,3,4]。管道 concatMapn=>concat 水管 tapn=>{console.log`computing${n}`}, concatMapn=>from[5,6,7,8] , NEVER.pipetakunteltimer2000//不发射任何东西,然后在2000毫秒后完成 .subscribebeval=>{console.logval},=>{},=>{console.log`end`}
这是一个有效的演示。

对您的代码进行一个小的调整就可以让它按照您想要的方式工作。与简单地返回concatMap中的所需可观测值不同,您可以返回一个可观测值,第一个可观测值发出所需可观测值,然后是一个不发出任何信息的可观测值,然后在延迟后完成

为此,我们可以使用和:

来自[1,2,3,4]。管道 concatMapn=>concat 水管 tapn=>{console.log`computing${n}`}, concatMapn=>from[5,6,7,8] , NEVER.pipetakunteltimer2000//不发射任何东西,然后在2000毫秒后完成 .subscribebeval=>{console.logval},=>{},=>{console.log`end`} 这是一个工作演示