Android: OutofMemoryError: Die Bitmap-Größe überschreitet das VM-Budget ohne Grund, den ich sehen kann
Ich habe eine OutOfMemory-Ausnahme mit einer Galerie von über 600x800 JPEGs.
Die Umgebun
Ich habe die Galerie mit JPG-Bildern im Format 600 x 800 Pixel verwendet.
Da mein Inhalt möglicherweise etwas komplexer als nur Bilder ist, habe ich für jede Ansicht ein RelativeLayout festgelegt, das ImageView mit JPG umschließt.
Um die Benutzererfahrung zu "beschleunigen", habe ich einen einfachen Cache mit 4 Slots, der (in einem Looper) ungefähr 1 Bild links und 1 Bild rechts zum angezeigten Bild vorabruft und diese in einer 4-Slot-HashMap speichert.
Die Platfor
Ich verwende AVD mit 256 RAM und 128 Heap-Größe mit einem 600x800-Bildschirm. Dies geschieht auch auf einem Entourage Edge-Ziel, mit der Ausnahme, dass das Debuggen auf dem Gerät schwieriger ist.
Das Proble
Ich habe eine Ausnahme bekommen:
OutofMemoryError: bitmap size exceeds VM budget
Und es passiert, wenn das fünfte Bild abgerufen wird. Ich habe versucht, die Größe meines Bild-Cache zu ändern, und es ist immer noch die gleiche.
Die seltsame Sache: Es sollte kein Speicherproblem geben
Um sicherzustellen, dass das Heap-Limit sehr weit von dem entfernt ist, was ich benötige, habe ich am Anfang ein 8-MB-Dummy-Array definiert und es nicht referenziert, sodass es sofort versendet wird. Es ist Mitglied des Aktivitätsthreads und wie folgt definiert:
static { @SuppressWarnings("unused")
byte dummy[] = new byte[ 8*1024*1024 ]; }
Das Ergebnis ist, dass der Heap fast 11 MB groß ist und alles kostenlos ist.Hinwei Ich habe diesen Trick nach dem Absturz hinzugefügt. Dadurch wird OutOfMemory seltener.
Jetzt benutze ich DDMS. Kurz vor dem Absturz (ändert sich nach dem Absturz nicht viel) zeigt DDMS:
ID Heap Size Allocated Free %Used #Objects
1 11.195 MB 2.428 MB 8.767 MB 21.69% 47,156
Und in der Detailtabelle wird Folgendes angezeigt:
Type Count Total Size Smallest Largest Median Average
free 1,536 8.739MB 16B 7.750MB 24B 5.825KB
Der größte Block ist 7.7MB. Und doch sagt der LogCat:
ERROR/dalvikvm-heap(1923): 925200-byte external allocation too large for this process.
Wenn Sie das Verhältnis von Median und Durchschnitt beachten, ist es plausibel anzunehmen, dass die meisten verfügbaren Blöcke sehr klein sind. Jedoch,there ist ein Block groß genug für die Bitmap, es ist 7.7M. Wieso reicht es noch nicht?
Hinweis: Ich habe eine Heap-Spur aufgezeichnet. Wenn man die Menge der zugewiesenen Daten betrachtet, fühlt es sich nicht so an, als wären mehr als 2 Millionen zugewiesen. Es stimmt mit dem Freispeicherbericht von DDMS überein.
Kann es sein, dass ich ein Problem wie die Haufenfragmentierung habe?Wie löse ich das Problem?Ist der Heap für alle Threads freigegeben?Kann es sein, dass ich die DDMS-Anzeige falsch interpretiere und wirklich keinen 900K-Block zuzuweisen habe? Wenn ja, kann mir bitte jemand sagen, wo ich das sehen kann?Danke vielmal
Meymann