当前位置: 首页 > 面试题库 >

哪种Android工具和方法最适合发现内存/资源泄漏?

卫学真
2023-03-14
问题内容

我已经开发了一个Android应用程序,而我正处于电话应用程序开发阶段,一切似乎都正常进行,您想宣告胜利并出货,但是您知道必须存在一些内存和资源泄漏在那里; Android上只有16mb的堆,而且显然很容易在Android应用中泄漏。

我一直在环顾四周,到目前为止,我们只能挖掘有关“ hprof”和“ traceview”的信息,而且都没有得到很多好评。

您遇到或开发了哪些工具或方法,并希望在OS项目中共享这些工具或方法?


问题答案:

我发现开发Android应用程序时最常见的错误之一是“ java.lang.OutOfMemoryError:位图大小超出VM预算”错误。我在更改方向后频繁使用许多位图在活动中发现此错误:活动被销毁,再次创建,布局从XML中“膨胀”,消耗了位图可用的VM内存。

垃圾回收器未正确释放先前活动布局上的位图,因为它们已交叉引用其活动。经过多次实验,我发现了一个很好的解决方案。

首先,在XML布局的父视图上设置“ id”属性:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
     android:layout_width="fill_parent"
     android:layout_height="fill_parent"
     android:id="@+id/RootView"
     >
     ...

然后,在Activity的onDestroy()方法上,调用unbindDrawables()方法,将引用传递给父View,然后执行System.gc()

@Override
protected void onDestroy() {
    super.onDestroy();

    unbindDrawables(findViewById(R.id.RootView));
    System.gc();
}


private void unbindDrawables(View view) {

    if (view.getBackground() != null) {
        view.getBackground().setCallback(null);
    }

    if (view instanceof ViewGroup) {
        for (int i = 0; i < ((ViewGroup) view).getChildCount(); i++) {
            unbindDrawables(((ViewGroup) view).getChildAt(i));
        }

        ((ViewGroup) view).removeAllViews();
    }
}

此unbindDrawables()方法以递归方式探索视图树,并:

删除所有背景可绘制对象上的回调
在每个视图组上删除子级



 类似资料:
  • 在哪种情况下会发生这种情况?

  • 我担心从泄漏金丝雀回来的信息。它显示了在UI上声明的所有变量,如片段中的材料按钮、材料卡片视图、文本视图、图像视图等,都导致了内存泄漏。我不知道为什么会这样。

  • 哪些资源适合存入 oss ,哪些资源则自行管理?

  • 问题内容: 由于这个问题很受欢迎,因此我认为对其进行更新很有用。 让我强调AviD对这个问题给出 的正确答案 : 您不应在Cookie中存储任何需要加密的数据。 而是在cookie中存储一个大小合适的(128位/ 16字节)随机密钥,并在cookie的密钥中标识要在服务器上保持安全的信息。 我正在寻找有关“最佳”加密cookie加密算法的信息。 我有以下要求: 它必须快速 加密和解密(几乎)每个请

  • 问题内容: 我认为我的android应用正在泄漏内存。我不是绝对确定这是问题所在。 应用程序打开时经常崩溃,并且logcat尝试加载位图图像时会显示“内存不足”异常。 崩溃后,我重新打开了该应用程序,它运行正常。Logcat会显示许多“ gc”,并且JIT表会不时地向上调整大小,而不会向下调整,直到应用程序因内存不足错误而崩溃。 这听起来像是内存泄漏吗?如果是这样,我该如何定位和关闭泄漏点。 这是

  • 我有一个创建Presenter实例的活动。在Presenter层中,我从存储库中获取一个可观察的实例。然后,我使用Subscriber的子类订阅Observable,然后将结果订阅对象添加到CompositeSubscription。因为调用订阅服务器的onNext()后,我需要修改活动,所以我还将Presenter的引用传递给订阅服务器。 现在,我想知道引用是如何工作的,什么时候才有资格进行垃圾