我在读Angular Guide about Routing & Navigation.

他们使用此代码检索路由的param 'id',并使用它获得service服务的英雄:

ngOnInit() {
  this.route.params
    .switchMap((params: Params) => this.service.getHero(+params['id']))
    .subscribe((hero: Hero) => this.hero = hero);
}

但我不太明白在上述代码中使用switchMap运算符的目的是什么.

下面的代码不会是相同的吗?

ngOnInit() {
  this.route.params
    // NOTE: I do not use switchMap here, but subscribe directly
    .subscribe((params: Params) => {
      this.service.getHero(+params['id']).then(hero => this.hero = hero)
    });
}

推荐答案

switchMap通常用于由某个前置"事件/流"触发的异步操作.

与例如flatMapconcatMap不同的是,一旦下一个触发器发出,当前异步操作就会被取消并重新触发.

在您的情况下,这意味着,一旦路由参数发生变化,您的hero服务将自动使用更改的参数再次调用,上一次调用将被取消,这样您就不会收到过时的数据.

这对于可能需要超过200-300毫秒的搜索查询尤其有用,并且在用户键入时触发.

下面的代码不一样吗?

不是的.虽然在许多情况下它的行为可能是相同的,但如果您设想以下场景:

  1. 参数更改为"4"
  2. getHero(4)(非常慢的请求)
  3. 参数更改为"1"
  4. getHero(1)(快速请求)
  5. getHero(1) completes -> hero is "1"
  6. getHero(4) completes -> hero is now "4" but the last used param was "1"

在这种情况下,switchMap只会放弃getHero(4)调用,因为一旦发生新的触发器,它就过时了.

Angular相关问答推荐

Angular 17上的material 工具提示的自定义样式

Angular Signal只指一种类型,但这里用作值.ts(2693)''

如何在每次Angular 编译之前执行脚本(esbuild)

[已解决]如何在模块ngDoBootstrap中测试Angular 自定义元素和做覆盖

MAT-复选框更改事件未在onSubscriberCheck函数中返回选中的值

Angular 单调服务已多次创建

除非将 signal.set 作为间隔的一部分调用,否则Angular 信号效果不会执行

如何从2个api获取数据并查看Angular material 表中的数据?

没有调用订阅的原因是什么?

Angular 获取视频持续时间并存储在外部变量中

如何以Angular 显示动态视图模型

关闭 Dynamsoft Web Twain 弹出窗口

angular 13 ng 构建库失败(ivy部分编译模式)

错误:您要查找的资源已被删除、名称已更改或暂时不可用

Angular-CLI 代理到后端不起作用

Angular 2 - 全局 CSS 文件

如何以编程方式触发`valueChanges`?

具有多个订阅者的 Angular 2 Observable

Angular 2 router.navigate

IE11中的Angular4应用程序运行问题