尽管可用内存可用,但OutOfMemory错误

Eig*_*ght 13 android jvm bitmap dalvik android-3.0-honeycomb

我看到一个非常奇怪的问题.基本上有时大的位图内存分配将失败,即使显然有大量的内存.有很多帖子似乎问了类似的问题,但它们都与蜂窝前的安卓有关.我的理解是图像现在分配在堆上,而不是一些外部存储器.无论如何,请看下面这个日志:

    10-14 13:43:53.020: INFO/dalvikvm-heap(31533): Grow heap (frag case) to 40.637MB for 942134-byte allocation
    10-14 13:43:53.070: DEBUG/dalvikvm(31533): GC_FOR_ALLOC freed 126K, 11% free 41399K/46343K, paused 31ms
    10-14 13:43:53.130: DEBUG/dalvikvm(31533): GC_FOR_ALLOC freed 920K, 13% free 40478K/46343K, paused 30ms
    10-14 13:43:53.180: DEBUG/dalvikvm(31533): GC_FOR_ALLOC freed 1026K, 13% free 40479K/46343K, paused 30ms
    10-14 13:43:53.250: DEBUG/dalvikvm(31533): GC_FOR_ALLOC freed 931K, 12% free 41193K/46343K, paused 31ms
    10-14 13:43:53.250: INFO/dalvikvm-heap(31533): Grow heap (frag case) to 41.313MB for 1048592-byte allocation
    10-14 13:43:53.280: DEBUG/dalvikvm(31533): GC_FOR_ALLOC freed <1K, 11% free 42217K/47431K, paused 31ms
    10-14 13:44:01.520: DEBUG/dalvikvm(31533): GC_CONCURRENT freed 3493K, 15% free 40646K/47431K, paused 3ms+9ms
    10-14 13:44:08.130: DEBUG/dalvikvm(31533): GC_EXPLICIT freed 16461K, 47% free 25527K/47431K, paused 3ms+6ms
    10-14 13:44:09.150: DEBUG/dalvikvm(31533): GC_FOR_ALLOC freed 1007K, 45% free 26191K/47431K, paused 35ms
    10-14 13:44:09.160: INFO/dalvikvm-heap(31533): Grow heap (frag case) to 29.334MB for 3850256-byte allocation
    10-14 13:44:09.200: DEBUG/dalvikvm(31533): GC_CONCURRENT freed 0K, 37% free 29951K/47431K, paused 2ms+4ms
    10-14 13:44:11.970: DEBUG/dalvikvm(31533): GC_FOR_ALLOC freed 1878K, 38% free 29784K/47431K, paused 37ms
    10-14 13:44:12.410: DEBUG/dalvikvm(31533): GC_FOR_ALLOC freed 62K, 36% free 30441K/47431K, paused 32ms
    10-14 13:44:12.440: DEBUG/dalvikvm(31533): GC_FOR_ALLOC freed <1K, 32% free 32325K/47431K, paused 32ms
    10-14 13:44:12.440: INFO/dalvikvm-heap(31533): Forcing collection of SoftReferences for 3850256-byte allocation
    10-14 13:44:12.480: DEBUG/dalvikvm(31533): GC_BEFORE_OOM freed 124K, 33% free 32200K/47431K, paused 37ms
    10-14 13:44:12.480: ERROR/dalvikvm-heap(31533): Out of memory on a 3850256-byte allocation.
Run Code Online (Sandbox Code Playgroud)

我为包含这么多日志而道歉,我希望它是相关的.我读它的方式是系统不断重新调整堆大小,直到它最终达到堆最大值.然后,我们请求一个特别大的分配失败.显然,有足够的可用内存(约15兆).这是否意味着堆内部碎片化,并且没有足够大的连续内存段来处理我们的分配?如果是这样的话我该怎么办?如果那不是它,那么呢?

提前致谢.

heg*_*ege 16

怪异的行为是因为位图被分配在本地堆,而不是在收集垃圾,但是Android只能跟踪在垃圾回收堆中的对象.从Android 2.2(或2.3或许)可以改变,如果你进行堆转储,分配的位图也是可见的.

回到问题,您的问题很可能是您手动加载的位图未正确释放.一个典型的问题是某些回调仍然设置或视图仍然引用位图.另一个常见的问题是,如果你手动加载大位图(而不是作为资源),你将需要在它们不再需要时调用它们上的recycle(),这将从本机内存释放位图所以垃圾收藏家将能够正常工作.(气相色谱只能看到物体的GC堆,并且不无其反对自由地从本机堆释放内存,居然甚至不关心它.)

我一直有这个小宝宝:

public static void stripImageView(ImageView view) {
    if ( view.getDrawable() instanceof BitmapDrawable ) {
        ((BitmapDrawable)view.getDrawable()).getBitmap().recycle();
    }
    view.getDrawable().setCallback(null);
    view.setImageDrawable(null);
    view.getResources().flushLayoutCache();
    view.destroyDrawingCache();
}
Run Code Online (Sandbox Code Playgroud)