Kotlin Singleton的这种实现方式对于垃圾回收将变得可以理解吗?

时间:2018-11-27 03:03:36

标签: android performance kotlin garbage-collection

我让此类像单身人士一样工作(实例无法确保再次创建):

class FooInteractorFactory(private val someEvent: SomeEvent) {

    companion object {

        lateinit var fooFactory: FooInteractorFactory

        fun initialize(someEvent: SomeEvent) {
            fooFactory = FooInteractorFactory(someEvent)
        }
    }

    fun createSomeObject(): SomeObject {
        return SomeObject(someEvent)
    }

}

该“单身”正在此类中初始化:

class FooImpl : SomeEvent {

    init {
        FooInteractorFactory.initialize(this)
    }

    ...
}

FooImpl在活动的生命周期函数onCreate()中实例化:

class MainActivity : AppCompatActivity() {


    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)
       val foompl = FooImpl()
    }

    ...

}

我在这里的问题是FooInteractorFactorySomeEventSomeObject,其中有些会泄漏或不符合垃圾收集的条件?

如文档所述,

  

仅当垃圾回收器可以回收其定义的类加载器时,才可以卸载类或接口。

这将符合资格,但我不确定。我只是添加了应用程序LeakCanary,但是,泄漏从未发生过。

我想根据你们每个人的经验来确定。

编辑

这是FooInteractorFactory在反编译的Java代码中的样子:

public final class FooInteractorFactory {
   private final SomeEvent someEvent;
   @NotNull
   public static FooInteractorFactory fooFactory;

   @NotNull
   public final FooInteractorFactory createSomeObject() {
      return new SomeObject(this.someEvent);
   }

   public FooInteractorFactory(@NotNull SomeEvent someEvent) {
      this.someEvent = someEvent;
   }


   public static final class Companion {
      @NotNull
      public final FooInteractorFactory getFooFactory() {
         return FooInteractorFactory.access$getFooFactory$cp();
      }

      public final void setFooFactory(@NotNull FooInteractorFactory var1) {
         FooInteractorFactory.fooFactory = var1;
      }

      public final void initialize(@NotNull SomeEvent someEvent) {
         ((FooInteractorFactory.Companion)this).setFooFactory(new FooInteractorFactory(someEvent));
      }
  }

}

FooInteractorFactory是同一类的静态引用。

1 个答案:

答案 0 :(得分:0)

AFAIK LeakCanary仅检测到泄漏的活动,因此它并非旨在检测所有内存泄漏(最终,现在应该如何对哪个实例进行垃圾回收,而应该不进行垃圾回收?)。

此外,您作为报价单附加的内容是Class<?>,而不是实例。我的意思是,它说的是整个Class定义,这些定义存储在永久代或元空间(取决于Java版本)中。

关于您的问题:垃圾收集器通常以另一种方式工作-它从名为GC根的引用开始,然后通过这些根中的引用遍历所有对象,将它们标记为“有效”,并从所有未标记为活动的对象(我的意思是,无法通过GC根目录获得这些对象)。称为GC根的引用是:

  1. 局部变量
  2. static变量
  3. 有效的Thread s
  4. JNI参考

如果您没有定义自己的Class或弄乱了它们的生命周期,我怀疑您提到的ClassLoader个对象是否将从JVM中卸载。 谈论实例:

  

我让这个类像单身人士一样工作(实例没有被确保可以重新创建)

如果comanion的对象fooFactory引用了对象A,然后又重新分配了对象B,则如果A没有被其他GC根目录或中间引用引用可以通过GC根目录获得,而不是在几个GC周期中,将立即收集该实例。

所有其他实例也是如此。

相关问题