Angular清除订阅的更好方法

时间:2019-06-21 11:04:10

标签: angular rxjs observable rxjs-subscriptions rxjs-observables

有很多方法可以有效地处理一个组件中的多个订阅,我这里有2种方法,想知道哪种方法更有效以及为什么?

方法1:使用数组

第1步:创建数组

private subscriptionArray: Subscription[];

第2步:将预订添加到阵列

this.subscriptionArray.push(this._storeManagementHttp.createStore(newStore).subscribe(resp => {
  this._toast.success('New store created');
}));

第3步:迭代每个订阅并取消订阅

this.subscriptionArray.forEach(subs => subs.unsubscribe());

方法2

第1步:创建新的订阅

private subscriptions = new Subscription();

第2步:添加订阅

this.subscriptions.add(this._storeManagementHttp.createStore(newStore).subscribe(resp => {
  this._toast.success('New store created');
  this._router.navigate(['/store-management']);
}));

第3步:清除订阅

this.subscriptions.unsubscribe();

4 个答案:

答案 0 :(得分:1)

您也可以这样做,在这种情况下您无需运行循环

private destroy$ = new Subject();

myservice.megohd().pipe(takeUntil(destroy$)).subscribe();

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

在此处阅读(https://www.learnrxjs.io/operators/filtering/takeuntil.html

答案 1 :(得分:1)

您还有第三个选项,这是一个自定义RxJS运算符。

我创建了一个,发现Netanel Basal也找到了它,因此我将给出他的干净代码。

您可以安装UntilDestroyed或使用代码:

function isFunction(value) {
  return typeof value === 'function';
}

export const untilDestroyed = (
  componentInstance,
  destroyMethodName = 'ngOnDestroy'
) => <T>(source: Observable<T>) => {
  const originalDestroy = componentInstance[destroyMethodName];
  if (isFunction(originalDestroy) === false) {
    throw new Error(
      `${
        componentInstance.constructor.name
      } is using untilDestroyed but doesn't implement ${destroyMethodName}`
    );
  }
  if (!componentInstance['__takeUntilDestroy']) {
    componentInstance['__takeUntilDestroy'] = new Subject();

    componentInstance[destroyMethodName] = function() {
      isFunction(originalDestroy) && originalDestroy.apply(this, arguments);
      componentInstance['__takeUntilDestroy'].next(true);
      componentInstance['__takeUntilDestroy'].complete();
    };
  }
  return source.pipe(takeUntil<T>(componentInstance['__takeUntilDestroy']));
};

然后您的订阅变为

this.myService.subject.pipe(untilDestroyed(this)).subscribe(...);

请注意,由于AOT编译,您必须编写ngOnDestroy方法,否则操作员将无法从头开始创建它。

答案 2 :(得分:0)

我希望使用方法2。

方法1没问题。

  

效果很好。这种方法的问题是我们   将可观察的流与普通的旧式命令式逻辑混合在一起。

方法2是增强此方法的内置机制。

阅读here

答案 3 :(得分:0)

您提供了很好的答案,尽管我会尽可能避免使用上述所有方法,而建议使用duct_ret = Duct(0.4, 0.3, 10, 18, 19.5, 3, 1, 1010, 1.2) #---- INPUT #-- Geometry import ENGINE as EN duct_ret.c_s = EN.cross_section(duct_ret.width, duct_ret.height) print(duct_ret.c_s) print(EN.Tair_outlet(duct_ret.Ts_int, duct_ret.Tair_inlet, duct_ret.hint, duct_ret.c_s, duct_ret.v_air, duct_ret.rho_air, duct_ret.cp_air, duct_ret.L)) '管道,即允许有角度地进行订阅和取消订阅。

让我们考虑一些可观察对象,比如说5个可观察对象

async

为避免订阅所有这些内容,我们可以创建一个observale1$: Observable<IDataDto1>; observale2$: Observable<IDataDto2>; observale3$: Observable<IDataDto3>; observale4$: Observable<IDataDto4>; observale5$: Observable<IDataDto5>; ,说Observable

v$

通过上述操作,我们可以将我们的 component.html 包装在 import { forkJoin } from 'rxjs'; v$ = forkJoin({ observale1: observale1$, observale2: observale2$, observale3: observale3$, observale4: observale4$, observale5: observale5$ }); 中,并允许angular自动订阅和取消订阅

*ngIf
相关问题