首页 文章

AlertDialog.Builder活动泄漏

提问于
浏览
2

当我们创建AlertDialog.Builder时,我们传递将显示Dialog的Activity的上下文 .

AlertDialog.Builder builder = new Builder(getActivity()); <<< Activity Context passed as argument
      mAlertDialog = builder.create();
      mAlertDialog.show();

现在要避免ActivityLeakedException,我们必须在销毁Activity时解除()对话框 . (让我们说屏幕上的roatation) . 这个dismiss()将在Dialog引用上调用,而不是在构建器上调用 . 即使我们在Dialog上调用了dismiss(),构建器也无法知道Activity是如何被销毁的,它应该释放上下文,因此构建器持有对Activity Context的引用 . 这不是泄漏活动吗?

1 回答

  • 1

    虽然这可能无法完全回答您的问题,但以下是一些观察:

    只要构建器"is alive"垃圾收集器可能无法触及 Activity .

    现在,代码中的代码片段通常是在UI线程上执行的某些方法的一部分(因为涉及到UI元素 - AlertDialog ) .

    AlertDialog.Builder 实例是在该方法内创建的,因此一旦方法完成就有资格进行垃圾收集,因为没有任何东西可以保存对它的引用 .

    另一方面,活动将至少在 onPause() 被调用并返回之前 .

    这不是在泄漏活动吗?

    只要该方法在UI线程上运行即可 . 在其他情况下(例如 AsyncTask ),使用 WeakReference 可能是个好主意 . 或者尽可能使用应用程序上下文(例如使用 SQLiteOpenHelper ) .

    顺便说一下,最近我有一个 AlertDialog ,它在方向变化时消失了而没有我解雇它(AS模拟器,Lollipop) . Logcat在 WindowManager 上显示了一条消息,提到我的 Dialog 为"leaked window",所以我认为现在解雇 AlertDialog 对于避免内存泄漏非常重要 .

    由于我想保持对话框(以及到目前为止的用户输入),我切换到 AlertDialog -as- DialogFragment 解决方案,如文档中的sample . 此后,警告消息尚未显示 .

相关问题