【问题标题】:Is it recommended to call Disposable.dispose() as soon as a subscription completes work?是否建议在订阅完成后立即调用 Disposable.dispose()?
【发布时间】:2017-06-18 12:24:45
【问题描述】:

我有一个Activity,我在其中创建和订阅Single 类的多个实例(每个实例都在单独的后台线程中做一些工作)。对于每个订阅,我将创建的Disposable 实例添加到CompositeDisposable 实例,该实例的范围为Activity。当Activity 被销毁时,我正在调用CompositeDisposable.clear() 方法来处理Activity 中的所有订阅。当然,这意味着所有Disposable 实例(包括那些已完成工作的订阅)都在我的Activity 中徘徊,直到Activity 被销毁。

这样可以吗,还是应该在每次特定的Single 实例完成工作时为每个单独的订阅调用Disposable.dispose()(即当SingleObserver 收到onSuccessonError 回调时)?后一种方法的问题是我必须跟踪哪个Disposable 链接到哪个SingleObserver,这违背了使用CompositeDisposable 的意义。

【问题讨论】:

    标签: android rx-java2


    【解决方案1】:

    不,你不应该。当 Observable 完成时,Observable 会自行处理。这是Observable contract的一部分:

    当 Observable 向其观察者发出 OnError 或 OnComplete 通知时,这将结束订阅。观察者不需要发出 Unsubscribe 通知来结束 Observable 以这种方式结束的订阅。

    【讨论】:

      【解决方案2】:

      Yosriz's answer 是正确答案,但如果您确实想在Single 订阅完成工作后立即从您的CompositeDisposable 实例中删除Disposable 实例(并且没有Disposable 实例挂起),然后我整理了以下抽象类:

      public abstract class MySingleObserver<T> implements SingleObserver<T> {
      
          private Disposable disposable;
      
          @Override
          public void onSubscribe(@NonNull Disposable disposable) {
              this.disposable = disposable;
              onStart();
          }
      
          public Disposable getDisposable() {
              return disposable;
          }
      
          public abstract void onStart();
      }
      

      您可以将此类的具体扩展作为SingleObserver 传递给您的Single 订阅,如下所示:

      Single.just(1)
            .subscribe(new MySingleObserver<Integer>() {
      
                @Override
                public void onStart() {
                    MyActivity.this.myCompositeDisposable.add(getDisposable());
                    // do something further
                }
      
                @Override
                public void onSuccess(@NonNull Integer success) {
                    MyActivity.this.myCompositeDisposable.remove(getDisposable());
                    // do something further
                }
      
                @Override
                public void onError(@NonNull Throwable error) {
                    MyActivity.this.myCompositeDisposable.remove(getDisposable());
                    // do something further
                }
            });
      

      【讨论】:

      • 请问像这样从 CompositeDisposable 中删除它们有什么好处?内存管理稍微好一点?
      • 是的,纯粹是为了不让他们在记忆中停留的时间超过他们需要的时间。但我可以想象一个 Disposable 对象已被“丢弃”,但没有非常大的内存占用,因此如果您可以将 Disposable 对象持有的时间超过严格必要的时间,请随意忽略这一点。跨度>
      【解决方案3】:

      没有。它会在需要时自动处理。

      【讨论】:

      • 请注意,这已经在此线程中接受的答案中说过。见here。不过还是谢谢你的回答。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2014-04-21
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-06-17
      • 2020-03-26
      • 2021-06-19
      相关资源
      最近更新 更多