【问题标题】:Should I complete BehaviorSubject on the component destroy – Angular2我应该在组件销毁上完成 BehaviorSubject – Angular2
【发布时间】:2021-09-15 20:48:08
【问题描述】:

我在组件中提供了一项服务,因此如果要销毁该组件,它会运行ngOnDestory。每个订阅都使用takeUntil(this.destory$)(在组件的ngOnDestory 钩子上发出)或async 管道运行,因此当组件销毁时,所有内容都会取消订阅。

问题是,如果我在服务中有一个 BehaviorSubject,我应该在服务的 ngOnDestory 中运行它的 .complete() 和/或 .unsubscribe() 方法,还是按原样运行?

【问题讨论】:

    标签: angular rxjs behaviorsubject subject


    【解决方案1】:

    是的,您应该取消订阅ngOnDestroy;如果主题在服务内部,则不一定完成主题,因为其他组件可能仍在使用主题并且仍然需要它才能正常工作。

    服务是单例的,但它们的生命周期取决于提供它们的注入器。如果您的服务是在根注入器中提供的,它的生命周期与您的应用程序一样长,因此当您再次创建需要该主题的组件时,如果不进行某种重新初始化,您将无法重用它。

    您提到您确实有 takeUntil(this.destroy$),这不应该导致内存泄漏,但请务必在您的 this.destroy$ 上调用 complete ngOnDestroy

    ngOnDestroy() {
      this.destroy$.next();
      this.destroy$.complete();
    }
    

    【讨论】:

    • 只是想补充一下这个答案:不久前我写了一篇文章,描述了为什么在 RxJS 中使用主题时会发生内存泄漏。 Link here.
    • 很明显,如果主题是以根目录提供的,我不应该竞争它。我问如果不是单例我应该这样做吗?
    • 你不应该完成它,只要确保你没有内存泄漏。根据您提供的代码,您应该没有完成服务中的主题。
    • @AndreiGătej 从您的文章中我是否正确理解了,由于内存泄漏的原因是过时的订阅,如果我取消了所有订阅者的订阅,我不需要完成主题,因为它会被正确销毁本身,连同组件?
    • @RomanovEugene 是的,例如,如果主题是在一个组件中创建的,那么该组件是唯一拥有对该主题的引用的东西。因此,如果组件被销毁,则根本不再引用主题,因此可以安全地对它进行垃圾回收。 Completing the subject 只激活一个标志并向所有主题的订阅者发送完整的通知。
    猜你喜欢
    • 2017-01-21
    • 2017-09-07
    • 2016-12-06
    • 1970-01-01
    • 1970-01-01
    • 2017-03-18
    • 2017-11-20
    • 1970-01-01
    • 2015-11-21
    相关资源
    最近更新 更多