Recogida de basura GridView de Android (GC_EXTERNAL_ALLOC) <1K excesivamente, causando una interfaz de usuario muy intermitente

He estado mirando esto por mucho tiempo y finalmente decidí publicar – mi 2xN GridView, que consta de celdas con una sola imagen y un pedazo de texto es muy agitado muchas veces (pero a veces perfectamente liso). Al examinar la salida logcat, veo cosas como esta una vez que empiezo a desplazarse (solo hay 12 elementos en la lista):

10-25 17:28:40.420: D/dalvikvm(12159): GC_EXTERNAL_ALLOC freed 6K, 47% free 3383K/6279K, external 2044K/2161K, paused 38ms 10-25 17:28:40.510: D/dalvikvm(12159): GC_EXTERNAL_ALLOC freed <1K, 47% free 3383K/6279K, external 2044K/2161K, paused 36ms 10-25 17:28:40.600: D/dalvikvm(12159): GC_EXTERNAL_ALLOC freed <1K, 47% free 3383K/6279K, external 2044K/2161K, paused 40ms 10-25 17:28:41.805: D/dalvikvm(12159): GC_EXTERNAL_ALLOC freed 1K, 47% free 3383K/6279K, external 2044K/2161K, paused 34ms 10-25 17:28:41.840: D/dalvikvm(12159): GC_EXTERNAL_ALLOC freed <1K, 47% free 3383K/6279K, external 2044K/2161K, paused 25ms 10-25 17:28:41.880: D/dalvikvm(12159): GC_EXTERNAL_ALLOC freed <1K, 47% free 3383K/6279K, external 2044K/2161K, paused 25ms 10-25 17:28:41.910: D/dalvikvm(12159): GC_EXTERNAL_ALLOC freed <1K, 47% free 3383K/6279K, external 2044K/2161K, paused 20ms 10-25 17:28:41.940: D/dalvikvm(12159): GC_EXTERNAL_ALLOC freed <1K, 47% free 3383K/6279K, external 2044K/2161K, paused 18ms 

Esto fue sólo una película simple al final de la lista y copia de seguridad. Muy agitado. Si sigo desplazándome hacia arriba y hacia abajo, el GC sigue avanzando por unos 5-6 rollos, luego se detiene. Pero tan pronto como presione Menú que trae un menú de 2 entradas o cambiar las actividades y volver, GC vuelve también.

Desactivé asignaciones de mapa de bits para la imagen – el mismo problema. Mis células están esencialmente vacías, pero el GC todavía sucede.

Me puse en contacto con Romain Guy que dijo que debería intentar el seguimiento de la asignación. Corrí y seguí rastreando, pero no vi ninguna asignación en mi propio código. Vi asignaciones seguidas de llamadas a com.android.internal.os.BinderInternal $ GcWatcher asignado en finalize, que coincide con el número de líneas GC en logcat. Aquí está todo el volcado de Asocation Tracker (o como una imagen que es más fácil de analizar):

 1 24 org.apache.harmony.dalvik.ddmc.Chunk 5 org.apache.harmony.dalvik.ddmc.DdmServer dispatch 2 12 java.lang.Integer 5 java.lang.Integer valueOf 3 24 byte[] 5 dalvik.system.NativeStart run 4 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 5 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 6 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 7 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 8 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 9 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 10 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 11 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 12 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 13 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 14 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 15 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 16 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 17 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 18 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 19 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 20 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 21 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 22 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 23 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 24 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 25 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 26 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 27 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 28 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 29 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 30 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 31 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 32 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 33 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 34 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 35 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 36 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 37 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 38 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 39 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 40 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 41 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 42 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 43 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 44 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 45 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 46 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 47 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 48 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 49 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 50 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 51 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 52 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 53 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 54 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 55 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 56 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 57 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 58 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 59 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 60 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 61 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 62 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 63 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 64 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 65 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 66 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 67 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 68 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 69 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 70 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 71 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 72 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 73 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 74 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 75 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 76 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 77 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 78 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 79 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 80 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 81 8 com.android.internal.os.BinderInternal$GcWatcher 2 com.android.internal.os.BinderInternal$GcWatcher finalize 82 24 java.lang.ref.WeakReference 2 com.android.internal.os.BinderInternal$GcWatcher finalize 83 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 84 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 85 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 86 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 87 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 88 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 89 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 90 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 91 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 92 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 93 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 94 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 95 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 96 8 com.android.internal.os.BinderInternal$GcWatcher 2 com.android.internal.os.BinderInternal$GcWatcher finalize 97 24 java.lang.ref.WeakReference 2 com.android.internal.os.BinderInternal$GcWatcher finalize 98 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 99 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 100 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 101 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 102 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 103 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 104 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 105 8 com.android.internal.os.BinderInternal$GcWatcher 2 com.android.internal.os.BinderInternal$GcWatcher finalize 106 24 java.lang.ref.WeakReference 2 com.android.internal.os.BinderInternal$GcWatcher finalize 107 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 108 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 109 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 110 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 111 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 112 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 113 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 114 8 com.android.internal.os.BinderInternal$GcWatcher 2 com.android.internal.os.BinderInternal$GcWatcher finalize 115 24 java.lang.ref.WeakReference 2 com.android.internal.os.BinderInternal$GcWatcher finalize 116 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 117 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 118 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 119 60 com.carrieriq.iqagent.client.metrics.ui.UI11 1 android.view.ViewRoot submitPointerMetrics 120 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 121 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 122 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 123 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 124 8 com.android.internal.os.BinderInternal$GcWatcher 2 com.android.internal.os.BinderInternal$GcWatcher finalize 125 24 java.lang.ref.WeakReference 2 com.android.internal.os.BinderInternal$GcWatcher finalize 126 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 127 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 128 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 129 60 com.carrieriq.iqagent.client.metrics.ui.UI11 1 android.view.ViewRoot submitPointerMetrics 130 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 131 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 132 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 133 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 134 8 com.android.internal.os.BinderInternal$GcWatcher 2 com.android.internal.os.BinderInternal$GcWatcher finalize 135 24 java.lang.ref.WeakReference 2 com.android.internal.os.BinderInternal$GcWatcher finalize 136 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 137 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 138 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 139 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 140 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 141 60 com.carrieriq.iqagent.client.metrics.ui.UI11 1 android.view.ViewRoot submitPointerMetrics 142 60 com.carrieriq.iqagent.client.metrics.ui.UI11 1 android.view.ViewRoot submitPointerMetrics 143 60 com.carrieriq.iqagent.client.metrics.ui.UI11 1 android.view.ViewRoot submitPointerMetrics 144 20 java.util.ArrayList 19 android.os.MessageQueue <init> 145 36 android.os.MessageQueue 19 android.os.Looper <init> 146 24 android.os.Looper 19 android.os.Looper prepare 147 144 java.lang.Object[] 19 java.lang.ThreadLocal$Values initializeTable 148 32 java.lang.ThreadLocal$Values 19 java.lang.ThreadLocal initializeValues 149 16 java.lang.VMThread 1 java.lang.VMThread create 150 40 java.util.WeakHashMap$Entry 1 java.util.WeakHashMap put 151 16 java.security.ProtectionDomain[] 1 java.security.AccessControlContext <init> 152 20 java.security.AccessControlContext 1 java.security.AccessController getContext 153 16 java.security.ProtectionDomain[] 1 java.security.AccessController getStackDomains 154 24 java.lang.String 1 java.lang.AbstractStringBuilder toString 155 48 char[] 1 java.lang.AbstractStringBuilder <init> 156 20 java.lang.StringBuilder 1 java.lang.Thread create 157 16 android.view.ViewRoot$2 1 android.view.ViewRoot handleLongPress 158 80 java.lang.Thread 1 android.view.ViewRoot handleLongPress 159 60 com.carrieriq.iqagent.client.metrics.ui.UI11 1 android.view.ViewRoot submitPointerMetrics 160 24 org.apache.harmony.dalvik.ddmc.Chunk 5 android.ddm.DdmHandleHeap handleREAQ 161 17 byte[] 5 android.ddm.DdmHandleHeap handleREAQ 162 24 org.apache.harmony.dalvik.ddmc.Chunk 5 org.apache.harmony.dalvik.ddmc.DdmServer dispatch 163 12 java.lang.Integer 5 java.lang.Integer valueOf 164 24 byte[] 5 dalvik.system.NativeStart run 

Como puede ver, los eventos que preceden directamente al GC y que ocurren entre cada GC, son casi los siguientes:

 107 20 java.util.concurrent.CopyOnWriteArrayList$ListIteratorImpl 1 java.util.concurrent.CopyOnWriteArrayList iterator 108 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 109 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 110 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 111 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 112 24 java.lang.ref.SoftReference 1 android.view.View buildDrawingCache 113 36 android.graphics.Bitmap 1 android.graphics.Bitmap nativeCreate 114 8 com.android.internal.os.BinderInternal$GcWatcher 2 com.android.internal.os.BinderInternal$GcWatcher finalize 115 24 java.lang.ref.WeakReference 2 com.android.internal.os.BinderInternal$GcWatcher finalize 

Realmente deseo que el rastreador de asignación me permita exportar todo el volcado con trazas de pila individuales, pero no lo hace, por lo que pegaré algunos rastros de pila aquí, la mayoría de los cuales tienen que ver con el dibujo:

Android.graphics.Bitmap:

 android.graphics.Bitmap nativeCreate Bitmap.java -2 true android.graphics.Bitmap createBitmap Bitmap.java 477 false android.view.View buildDrawingCache View.java 6716 false android.view.View getDrawingCache View.java 6567 false android.view.ViewGroup drawChild ViewGroup.java 1571 false android.view.ViewGroup dispatchDraw ViewGroup.java 1373 false android.widget.AbsListView dispatchDraw AbsListView.java 1627 false android.widget.GridView dispatchDraw GridView.java 1943 false android.view.View draw View.java 7022 false android.widget.AbsListView draw AbsListView.java 3005 false android.view.ViewGroup drawChild ViewGroup.java 1646 false android.view.ViewGroup dispatchDraw ViewGroup.java 1373 false android.view.View draw View.java 7022 false android.view.ViewGroup drawChild ViewGroup.java 1646 false android.view.ViewGroup dispatchDraw ViewGroup.java 1373 false android.view.ViewGroup drawChild ViewGroup.java 1644 false 

Java.util.concurrent.CopyOnWriteArrayList:

 java.util.concurrent.CopyOnWriteArrayList iterator CopyOnWriteArrayList.java 332 false android.view.ViewTreeObserver dispatchOnPreDraw ViewTreeObserver.java 570 false android.view.ViewRoot performTraversals ViewRoot.java 1293 false android.view.ViewRoot handleMessage ViewRoot.java 1899 false android.os.Handler dispatchMessage Handler.java 99 false android.os.Looper loop Looper.java 130 false android.app.ActivityThread main ActivityThread.java 3691 false java.lang.reflect.Method invokeNative Method.java -2 true java.lang.reflect.Method invoke Method.java 507 false com.android.internal.os.ZygoteInit$MethodAndArgsCaller run ZygoteInit.java 907 false com.android.internal.os.ZygoteInit main ZygoteInit.java 665 false dalvik.system.NativeStart main NativeStart.java -2 true 

Aquí está mi contenedor de GridView XML:

 <?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="fill_parent" android:layout_height="fill_parent" android:orientation="vertical" > <LinearLayout android:id="@+id/scroll_items_holder" android:layout_width="fill_parent" android:layout_height="fill_parent" android:layout_weight="1" android:background="@drawable/app_bg" android:orientation="vertical" > <LinearLayout android:id="@+id/buttonsLayout" android:layout_width="fill_parent" android:layout_height="wrap_content" android:gravity="center" > </LinearLayout> <GridView android:id="@+id/gridview" android:layout_width="fill_parent" android:layout_height="wrap_content" android:columnWidth="150dp" android:gravity="right" android:horizontalSpacing="0dp" android:listSelector="@null" android:numColumns="auto_fit" android:paddingLeft="5dp" android:paddingRight="5dp" android:stretchMode="columnWidth" android:verticalSpacing="10dp" /> </LinearLayout> <include layout="@layout/menu_bar_inc" /> </LinearLayout> 

Archivo XML para cada celda GridView:

 <?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:id="@+id/card" android:layout_width="fill_parent" android:layout_height="wrap_content" android:orientation="vertical" > <ImageView android:id="@+id/thumbnail" android:layout_width="fill_parent" android:layout_height="120dp" android:layout_marginLeft="5dp" android:layout_marginRight="5dp" android:layout_marginTop="5dp" android:scaleType="centerCrop" /> <TextView android:id="@+id/show_name" android:layout_width="fill_parent" android:layout_height="wrap_content" android:layout_marginLeft="5dp" android:layout_marginRight="5dp" android:ellipsize="marquee" android:maxLines="1" android:textColor="@color/white" android:textStyle="bold" /> </LinearLayout> 

Adaptador, la mayoría de los cuales está comentado:

 package com.tunerfish.tunerfish.adapters; import java.util.ArrayList; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.widget.BaseAdapter; import android.widget.TextView; import com.tunerfish.tunerfish.core.TfHomeActivity; import com.tunerfish.tunerfish.databasemanager.dataitem.EntityDataItem; import com.tunerfish.tunerfish.ui.R; public class TrendingGalleryAdapter extends BaseAdapter { // structure for dumb view holders public static class ViewHolder { public TextView showName; // public ImageViewWithLoader thumbnail; } // structure for actual data behind the ListView public static class EntityData { public EntityDataItem entityDataItem; } public final ArrayList<EntityData> mEntityDataList; private final LayoutInflater mInflater; public TrendingGalleryAdapter(TfHomeActivity context, ArrayList<EntityData> entityData) { mContext = context; mInflater = LayoutInflater.from(context); mEntityDataList = entityData; } @Override public int getCount() { return mEntityDataList.size(); } @Override public EntityData getItem(int position) { return mEntityDataList.get(position); } @Override public long getItemId(int position) { return position; } private final TfHomeActivity mContext; @Override public View getView(final int position, View inView, ViewGroup parent) { ViewHolder holder; if (inView == null) { holder = new ViewHolder(); inView = mInflater.inflate(R.layout.trending_item_mod, null); holder.showName = (TextView) inView.findViewById(R.id.show_name); // holder.thumbnail = (ImageViewWithLoader) inView.findViewById(R.id.thumbnail); inView.setTag(holder); } else { holder = (ViewHolder) inView.getTag(); } // reset some stuff // holder.thumbnail.getImageView().setImageBitmap(null); // holder.showName.setText(getItem(position).entityDataItem.getTitle()); // deal with thumbnails String thumbnailUrl = getItem(position).entityDataItem.getTrendingThumbnail(); // mContext.sendImgDownloadRequest(thumbnailUrl, holder.thumbnail.getImageView(), R.drawable.tunerfish_details_logo2); return inView; } } 

Por lo tanto, esta pregunta puede parecer larga, pero quería incluir la mayor cantidad de información posible. Encontré un problema relacionado de ListView Mucha colección de basura en un listview pero desafortunadamente no parece aplicarse a GridViews.

Además, no parece que estoy solo con este problema – un amigo mío me contactó para preguntar sobre exactamente el mismo problema en su aplicación, de forma totalmente independiente.

Mis dispositivos de prueba son OG Droid con CM 7.1 y Epic 4G Touch corriendo stock Gingerbread.

Entonces, ¿esto es un error de marco? ¿Estoy haciendo algo mal? ¿No incluyo un determinado parámetro?

Gracias.

Después de probar más cosas al azar, creo que fui capaz de resolver el problema configurando el scrollingCache de GridView a false en el XML. Ahora es suave.

http://developer.android.com/reference/android/widget/AbsListView.html#attr_android:scrollingCache

Por lo tanto, un ajuste que se supone que hace que el uso de GridView más memoria y sacar de la memoria caché más rápido en realidad hace justamente lo contrario debido a GC por lo que se agita. Desactivar la memoria caché utiliza menos memoria y ya no está interrumpida.

Este es un ganar-ganar en mi libro, y espero que ayude a alguien en el futuro (ಠ_ಠ Google).

Edit : Acabo de probarlo en un decente-ListView de ejecución, que de vez en cuando llamaría GC_EXTERNAL_ALLOC para liberar pequeñas cantidades de memoria. Eliminarla de un ListView eliminó muchas llamadas GC_EXTERNAL_ALLOC minúsculas y sólo queda una llamada GC_CONCURRENT mayor ocasional. Ahora un ListView que funciona correctamente es un ListView de gran rendimiento. Así que scrollingCache parece ser algo que evitar en cualquier lista y no debe estar habilitado por defecto IMO.

Esto también es un problema con ListViews, y la colección de basura stop-the-world frecuente provoca una mala experiencia del usuario final y lleva al usuario a culpar a Android por el rendimiento de la interfaz de usuario. Sin embargo, este problema también se puede resolver de la misma manera estableciendo scrollingCache a false.

Utilizando SimpleCursorAdapter con un diseño ListView de 2 líneas personalizado que se utiliza en ListActivity, no hay imágenes sólo texto y tengo CacheColorHint – # 00000000. Antes de comenzar voy a decir que una solución rápida es la eliminación de cachecolorhint, pero lo necesito por lo que no es una solución a la GC tan ….

He tenido problemas con este mismo problema ahora y en el pasado sin embargo esto lanza una bola curva en ella … Tengo dos aplicaciones que son esencialmente imágenes espejo de cada uno. Uno funcionará muy bien sin la recogida de basura desenfrenada en el logcat y se desplaza maravillosamente, el otro no funciona tan bien y nada, ninguna copia y pegado de código puede arreglarlo de uno a otro.

TAMBIÉN … A veces en la aplicación que no está funcionando tan bien, puedo conseguir que funcione cuando recurro a la lista de una consulta y utilizar un diseño ligeramente diferente para la vista de lista. No salte a conclusiones, porque si navego lejos y vuelvo, la misma consulta ordenada utilizando el adaptador de cursor simple en un diseño de elemento de lista de 2 líneas personalizadas hará que el GC de nuevo. En otras palabras, simplemente funcionará correctamente y otras veces no. Tenga en mente, tengo "scrollingCache" izquierda como el valor predeterminado en ambas aplicaciones y como he dicho que son copias de los demás.

Hace un tiempo me encontré con esto y fue capaz de resolver de alguna manera y no tenía nada que ver con ScrollingCache. Más bien tenía que ver con mi compilación compilar contra alguna versión antigua de Android (creo) Mi memoria no es 100% segura de esto, pero juro que la corrección estaba relacionada con un problema de compilación / compilador. Voy a publicar algo si recuerdo lo que lo arregló. Yo uso Surround por lo que estoy buscando cambios. Espero que esto tenga sentido

  • Desplazamiento inercial dentro de la aplicación Phonegap android (todos los teléfonos)
  • Android: Desplazamiento automático de texto en TextView
  • Cómo detener el desplazamiento interno de WebView en Android?
  • Sincronizar la posición de dos vistas ScrollView
  • Android personalizado listview muy lento al desplazarse
  • Evento de la galería a "cuando la imagen se centró"
  • Android: ¿Cómo puedo desactivar el desplazamiento de CalendarView
  • El desplazamiento de texto no funciona
  • Cómo utilizar RecyclerView.scrollToPosition () para mover la posición a la parte superior de la vista actual?
  • Barra de desplazamiento en android
  • Android: ¿Animación de Scroller?
  • FlipAndroid es un fan de Google para Android, Todo sobre Android Phones, Android Wear, Android Dev y Aplicaciones para Android Aplicaciones.