¿Qué es lo que hace Bitmap # recycle () en Android Honeycomb?

Estoy escribiendo una aplicación muy intensiva de memoria para Android Honeycomb, y he sido muy cuidadoso para recycle() Bitmap s sin usar siempre que sea posible; de hecho, esto es necesario para que la aplicación funcione en absoluto, ya que los Bitmap se están cambiando constantemente dentro y fuera de la memoria. Sin embargo, acabo de implementar onConfigurationChanged() en la Activity , y por lo que (por una serie de razones) estoy tratando de poner rutinas de liberación de memoria en onStop() .

Actualmente mi método onStop() :

  • establece algunas View s para mostrar un Drawable predeterminado;
  • llamadas recycle() en el Bitmap s utilizado anteriormente por estos View s;
  • nula referencias al Bitmap .

Desafortunadamente, con el generador de perfiles de memoria Eclipse, parece que esto no tiene ningún efecto en el uso de memoria en absoluto .

Como se puede imaginar, habiendo hecho tanto esfuerzo para liberar recursos en un lenguaje nominalmente recolectado de basura, habría esperado un poco más de efecto. Así que mi pregunta es: ¿qué hace recycle() hacer? ¿Realmente dispara la recolección de basura, o el sistema se aferra a la memoria, incluso si llama a System.gc() hasta que se siente la necesidad de deshacerse de algo?

NB Sé que Bitmap s no se celebran en realidad en el montón regular, pero pensé que llamar a recycle() era suficiente para asegurar que fueron abandonados fuera de la pila nativa.

PARTE DE LA RESPUESTA

He descubierto que si un ImageView contiene un Bitmap que ha sido reciclado, los datos de Bitmap se conservan en la memoria hasta que se setImageBitmap(null) en ImageView . Esto puede ser el caso si setImageResource(...) o setImageDrawable(...) son llamados (estaban, cargando en un parche relativamente pequeño de nueve-sin embargo, el análisis MAT muestra que esto no eliminó el Bitmap grande, que fue contenidos en los miembros privados de ImageView ). Simplemente llamar a esta función en onStop() ha eliminado aproximadamente 10 MB del montón de nuestra aplicación. Al parecer, esto puede no ser el caso de las compilaciones pre-Honeycomb de Android, sin embargo.

Como dice Justin, los datos de mapa de bits no están asignados en el montón de VM. Hay una referencia a él en el montón de VM (que es pequeño), pero los datos reales se asignan en el montón nativo por la biblioteca de gráficos Skia subyacente. [Tenga en cuenta que esto puede haber cambiado en los últimos niveles de Android, pero es cierto para 2.1 y 2.2] Cuando hace un recycle () que marca tanto la pequeña parte en el montón de VM y los datos reales en el montón nativo como libre y disponible para GC. Pero la colección real es realizada por dos mecanismos diferentes del GC. La porción en el montón de VM se recoge por el GC Davlik – y se puede ver que sucede a través de DDMS. Pero los datos de heap nativos son recogidos por el GC Skia, que parece ser más flojo (se ejecuta con menos frecuencia?). Esto significa que, incluso con riguroso recycle () s, es posible adelantarse a la GC nativa del montón. Afortunadamente hay mecanismos para monitorear el estado del montón nativo. Vea el OOM de BitmapFactory que me conduce las tuercas .

He descubierto que, en Honeycomb en adelante, si un ImageView contiene un Bitmap que ha sido reciclado, los datos de Bitmap se conservan en la memoria hasta setImageBitmap(null) se llama en el ImageView. Esto puede ser el caso si setImageResource(...) o setImageDrawable(...) son llamados (en este caso, un bitmap muy grande fue reemplazado con un parche nueve bastante pequeño, pero sólo cuando setImageBitmap(null) fue llamado antes de cargar el parche de nueve fue la memoria realmente eliminado).

Recycle libera la memoria nativa que se asigna al mapa de bits. El objeto de mapa de bits real permanecerá en el montón de Dalvik hasta la próxima recolección de basura (pero la memoria ocupada por este objeto es insignificante).

Por lo que sé, realmente no hay manera de volcar el montón nativo. Por lo que no será capaz de ver si los datos nativos del mapa de bits se ha ido a través de un volcado de montón. Debería ver, sin embargo, que la cantidad total de memoria que utiliza su aplicación disminuye. Esta pregunta debería ayudarte a descubrir las distintas formas de acceder a las estadísticas de uso de memoria de tu aplicación.

FlipAndroid es un fan de Google para Android, Todo sobre Android Phones, Android Wear, Android Dev y Aplicaciones para Android Aplicaciones.