22

在 Ice Cream Sandwich 中,当有一个包含 EditText 的 Activity 时,即使在用户离开 Activity 之后,EditText 也会保留 Activity 的 Context。为了证明这一点,我创建了 TestLeakActivity,它分配了一个大字节数组。由于 Activity 的 Context 永远不会被垃圾回收,因此字节数组会在堆上累积,最终导致 OutOfMemoryError。您可以使用 DDMS 堆工具观察堆增长,并且可以通过查看 Eclipse MAT 中的 HPROF 文件来跟踪对 EditText 类的未完成引用。要创建内存泄漏,请进入 LaunchActivity,然后继续启动并退出 TestLeakActivity。

启动活动.java
包 com.example.testleakproject;

导入android.app.Activity;
导入android.content.Intent;
导入android.os.Bundle;
导入android.view.View;
导入 android.view.View.OnClickListener;
导入android.view.ViewGroup;
导入android.widget.Button;
导入 android.widget.TextView;

公共类 LaunchActivity 扩展 Activity {
    @覆盖
    公共无效 onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        按钮按钮 = 新按钮(此);
        button.setText("开始 TestLeakActivity");
        button.setOnClickListener(new OnClickListener() {
            @覆盖
            公共无效 onClick(查看 v){
                Intent intent = new Intent(LaunchActivity.this, TestLeakActivity.class);
                开始活动(意图);
            }
        });

        ViewGroup 容器 = ((ViewGroup) findViewById(android.R.id.content));
        容器.addView(按钮);
    }
}
TestLeakActivity.java
包 com.example.testleakproject;

导入android.app.Activity;
导入android.os.Bundle;
导入android.view.ViewGroup;
导入 android.widget.EditText;

公共类 TestLeakActivity 扩展 Activity {
    私有字节[] mSomeBytes = 新字节[1048576];

    @覆盖
    公共无效 onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        EditText editText = new EditText(this);
        editText.setHint("TestLeakActivity");

        ViewGroup 容器 = ((ViewGroup) findViewById(android.R.id.content));
        容器.addView(editText);
    }
}
4

6 回答 6

9

这是一个已知错误,将在 ICS MR1 中修复。

于 2011-12-14T01:29:12.610 回答
7

直到现在还没有解决这个问题。(安卓 4.2.1)

于 2012-12-06T12:16:20.627 回答
5

我刚刚花了几个小时才发现我受到了这个问题的影响。

该问题似乎是由拼写检查器引起的。当我禁用 EditText 视图的建议时,一切都被正确地垃圾收集了。

mInputType = mText.getInputType();
mText.setInputType(mInputType | InputType.TYPE_TEXT_FLAG_NO_SUGGESTIONS);

我真的不想禁用它,因为许多用户想要拼写检查。因此,也许有一种方法可以在输入字段获得焦点时临时启用它。

如果您不需要拼写检查器,只需将其添加到布局 xml 中的 EditText 元素中:

android:inputType="textNoSuggestions"

这似乎也可以解决它。

编辑:

刚刚发现这个似乎相关的线程:Workaround SpellCheckerSession leak?

于 2013-03-03T20:30:29.603 回答
0

我也有同样的经历。我的 Gingerbread 设备都可以正常工作,但在我的 Galaxy Nexus 上测试这种情况是可以预见的。您所经历的可能是 MR1 和 4.0.3 更新推出如此之快的原因。

于 2011-12-18T18:19:08.723 回答
-2

您遇到了Android 资源中有关内存泄漏的部分中描述的情况。请参阅该页面以获取一些解决方案。

于 2011-12-14T00:14:01.400 回答
-2

我遇到了同样的问题,我通过隐藏对话框的 EditText ondismiss 来解决它。

  mEditText.setVisibility(View.GONE);
于 2013-08-03T00:17:30.700 回答