内存泄漏和内存不足错误 [英] Memory Leaks & OutOfMemoryError

查看:26
本文介绍了内存泄漏和内存不足错误的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

所以我试图找出我的应用程序崩溃的原因

So I am trying to find out why my app is crashing for

Fatal Exception: java.lang.OutOfMemoryError: Failed to allocate a 128887990 byte allocation with 16777216 free bytes and 76MB until OOM
   at java.lang.AbstractStringBuilder.enlargeBuffer(AbstractStringBuilder.java:95)
   at java.lang.AbstractStringBuilder.append0(AbstractStringBuilder.java:146)
   at java.lang.StringBuilder.append(StringBuilder.java:216)    

我已经阅读了几篇文章,但它们都指向位图图像,我没有使用任何位图,所以我想也许我有可能导致此问题的内存泄漏,所以我安装了leakcanary,它只显示以下泄漏:

I have read several post but they all point towards a bitmap image, I am not using any bitmaps, so then I thought maybe I have memory leaks which might cause this, so I installed leakcanary and it is only showing the following leak:

com.google.android.gms.internal.zzcfi.zzfus
references com.google.android.gms.common.api.internal.zzci.zzful
references com.google.android.gms.common.api.internal.zzck.zzfuk
com.tech.activity.dashboard instance

我在 Google、Stackoverflow、Github 和 Leak canary 上进行了搜索,但找不到关于这究竟是什么泄漏或如何修复它的参考.我相信这是来自我的 google play services location,但这会导致我看到的 OOM 错误吗?有人能指出我正确的方向吗?

I have searched on Google, Stackoverflow, Github and leak canary and I can not find reference to what this is exactly leaking or how to fix it. I believe this is coming from my google play services location, but could this cause my OOM error I am seeing? Can someone point me in the right direction?

** 编辑 **正如评论指出的那样,这应该是字符串构建器的问题,自从我第一次发布应用程序以来,我从未改变过我的字符串构建器的工作方式,这是我的 Stringbuilder,其源来自 AccessibilityNodeInfo,我在这里做错了吗?

** EDIT ** As a comment pointed out this is supposed to be a string builder issue, I have never changed how my string builder works since I first released the app, here is my Stringbuilder which the source comes from AccessibilityNodeInfo, am I doing something wrong here?

public void processEvent(final AccessibilityNodeInfo source)
{
    final StringBuilder sb = new StringBuilder();
    processSubEvent(source, 0, sb);

    processUIText(source, sb.toString().toLowerCase());
}

private void processSubEvent(final AccessibilityNodeInfo source, final int n, final StringBuilder sb) {
    for (int i = 0; i < n; ++i){
        sb.append("	");
    }

    if (source != null){
        sb.append(tools.getText(source));
        sb.append("
");
        final int childCount = source.getChildCount();

        for (int i = 0; i < childCount; i++)
        {
            //Log.e(TAG, "Last UI: " + lastUIText);
            AccessibilityNodeInfo child = source.getChild(i);
            processSubEvent(child, n + 1, sb);

            child.recycle();
            }
        }
}

这是如何使用信息的示例:

This is example how the information is being used:

private void processUIText(AccessibilityNodeInfo source, final String text)
{
   if (text.contains("hello") && !text.contains("hello again"){
        tools.showToast("Hello Reached");
   }
}

推荐答案

这是如何使用信息的示例:

This is example how the information is being used:

然后不要构建字符串.构建一个 boolean.类似的东西应该可以工作:

Then don't build a string. Build a boolean. Something akin to this should work:

class Whatever {
    private boolean helloSeen=false;
    private boolean helloAgainSeen=false;

    public void processEvent(final AccessibilityNodeInfo source)
    {
        processSubEvent(source);
    }

    private void processSubEvent(final AccessibilityNodeInfo source) {
        if (source != null){
            String text=tools.getText(source);

            if (text.contains("hello")) {
                helloSeen=true;
            }

            if (text.contains("hello again")) {
                helloAgainSeen=true;

            }

            if (!helloSeen || !helloAgainSeen) {
                final int childCount = source.getChildCount();

                for (int i = 0; i < childCount; i++)
                {
                    //Log.e(TAG, "Last UI: " + lastUIText);
                    AccessibilityNodeInfo child = source.getChild(i);
                    processSubEvent(child);

                    child.recycle();
                }
            }
        }
    }
}

processEvent() 返回后,helloSeenhelloAgainSeen 将反映您的消息是否在任何地方遇到.

After processEvent() returns, helloSeen and helloAgainSeen will reflect whether your messages were encountered anywhere.

这篇关于内存泄漏和内存不足错误的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆