在调查内存使用情况时,GC_FOR_ALLOC更“严重”吗?

2022-09-01 20:08:08

我目前正在调查我的Android应用程序的垃圾回收问题,我很好奇GC_FOR_ALLOC是否表明比其他GC消息(例如GC_CONCURRENT)更大的问题。

根据我的理解,GC_CONCURRENT正在做垃圾回收器应该做的事情。堆已达到特定限制,最好去清理内存。

GC_FOR_ALLOC向我表明,如果我试图创建一个对象并且没有内存来做这件事,那么更严重的事情正在发生。

GC 消息是否有优先级或“严重性”级别?


答案 1

从某种意义上说,它比 更严重,因为意味着没有足够的可用内存来满足分配请求,因此垃圾回收是必要的,而只是意味着 GC 感觉像在运行,通常是因为可用内存量在分配后变得低于某个阈值。GC_FOR_ALLOCGC_CONCURRENTGC_FOR_ALLOCGC_CONCURRENT

A 本身并不是应用程序中出现问题的迹象,但是:GC_FOR_ALLOC

  • Android 应用程序从一个小堆开始,当应用程序需要越来越多的内存时,该堆会增长(到一定程度),并且在增加堆的大小之前完成。在这种情况下是完全正常的。GC_FOR_ALLOCGC_FOR_ALLOC
  • 如果分配内存的速度快于并发 GC 有时间释放内存,这是不可避免的。而且,分配内存的速度比并发 GC 释放内存的速度快并没有什么本质上的错误。GC_FOR_ALLOC

Android上一种更严重的GC类型是 ,当分配请求失败时执行,即使在应用程序堆已经变得尽可能大时也是如此。当这种情况发生时,作为最后的手段,Dalvik也会尝试释放SoftReferences,然后再进行最后一次分配内存的尝试,如果失败,则引发OutOfMemory异常。GC_BEFORE_OOMGC_FOR_ALLOC

如果你好奇地查看这个逻辑的代码,它在dalvik.git/vm/alloc/Heap中.cpptryMalloc()

无论如何,如果您不介意,我怀疑查看logcat输出是调试垃圾回收问题的最有效方法。我不知道您遇到了什么具体问题,但是您是否研究过DDMS中的分配跟踪器等工具,并在该工具的帮助下分析堆转储?(例如,请参阅 http://android-developers.blogspot.se/2011/03/memory-analysis-for-android.html 以开始使用。hprof-conv


答案 2