it-swarm.com.de

Garbage Collector in Android

Ich habe viele Android Antworten gesehen, die darauf hindeuten, den Garbage Collector in bestimmten Situationen anzurufen.

Ist es empfehlenswert, den Garbage Collector in Android vor einer speicherhungrigen Operation anzufordern? Wenn nicht, sollte ich ihn nur aufrufen, wenn eine OutOfMemory -Fehler auftritt?

Gibt es andere Dinge, die ich verwenden sollte, bevor ich auf den Müllsammler zurückgreife?

102
hpique

Für Versionen vor .0 Honeycomb: Ja, do callSystem.gc().

Ich habe versucht, Bitmaps zu erstellen, habe aber immer "VM out of memory error" erhalten. Aber als ich zuerst System.gc() aufgerufen habe, war es OK.

Beim Erstellen von Bitmaps schlägt Android schlägt häufig fehl, wenn nicht genügend Arbeitsspeicher vorhanden ist, und versucht nicht, zuerst Garbage Collect durchzuführen. Rufen Sie daher System.gc() und auf Sie haben genug Speicher, um Bitmaps zu erstellen.

Ich denke, wenn Sie Objekte erstellen, wird System.gc Bei Bedarf automatisch aufgerufen, aber nicht zum Erstellen von Bitmaps. Es scheitert einfach.

Daher empfehle ich, System.gc() vor dem Erstellen von Bitmaps manuell aufzurufen.

139
steve

In der Regel ist es bei Vorhandensein eines Garbage Collectors nicht ratsam, den GC manuell aufzurufen . Ein GC ist nach heuristischen Algorithmen organisiert, die am besten funktionieren, wenn sie sich selbst überlassen bleiben. Das manuelle Aufrufen des GC verringert häufig die Leistung.

Gelegentlich kann es in relativ seltenen Situationen vorkommen, dass ein bestimmter GC einen Fehler macht, und ein manueller Aufruf des GC kann dann die Leistung verbessern -weise. Dies liegt daran, dass es nicht wirklich möglich ist, einen "perfekten" GC zu implementieren, der den Speicher in allen Fällen optimal verwaltet. Solche Situationen sind schwer vorherzusagen und hängen von vielen subtilen Implementierungsdetails ab. Die "gute Praxis" besteht darin, den GC von selbst laufen zu lassen. Ein manueller Anruf beim GC ist die Ausnahme, der erst in Betracht gezogen werden sollte, nachdem ein tatsächliches Leistungsproblem ordnungsgemäß festgestellt wurde.

115
Thomas Pornin

Nicht genügend Speicher in Android Anwendung ist sehr häufig, wenn wir die Bitmap nicht richtig behandeln. Die Lösung für das Problem wäre

if(imageBitmap != null) {
     imageBitmap.recycle();
     imageBitmap = null;
}
System.gc();
BitmapFactory.Options options = new BitmapFactory.Options();
options.inSampleSize = 3;
imageBitmap = BitmapFactory.decodeFile(URI, options);
Bitmap  scaledBitmap = Bitmap.createScaledBitmap(imageBitmap, 200, 200, true);
imageView.setImageBitmap(scaledBitmap);

Ich habe gerade versucht, die Bitmap zu recyceln, mit der Sie den verwendeten Speicherplatz freigeben können, sodass möglicherweise nicht genügend Speicherplatz vorhanden ist. Ich habe versucht, es hat bei mir funktioniert.

Wenn das Problem weiterhin besteht, können Sie auch diese Zeile hinzufügen

BitmapFactory.Options options = new BitmapFactory.Options();
options.inTempStorage = new byte[16*1024];
options.inPurgeable = true;

weitere Informationen finden Sie unter diesem Link

http://voices.yahoo.com/Android-virtual-machine-vm-out-memory-error-7342266.html


HINWEIS: Aufgrund der momentanen "Pause", die durch das Ausführen von gc verursacht wird, wird nicht empfohlen , dies vor jeder Bitmap-Zuweisung zu tun.

Optimales Design ist:

  1. Befreien Sie alle nicht mehr benötigten Bitmaps mit dem angezeigten Code if / recycle / null. (Machen Sie eine Methode, um dabei zu helfen.)

  2. System.gc();

  3. Ordnen Sie die neuen Bitmaps zu.

26
yogesh

Wenn Sie einen OutOfMemoryError erhalten, ist es normalerweise zu spät, den Garbage Collector aufzurufen ...

Hier ist ein Zitat von Android Entwickler:

Die meiste Zeit tritt die Speicherbereinigung aufgrund von Tonnen von kleinen, kurzlebigen Objekten auf, und einige Speicherbereiniger, wie generationsübergreifende Speicherbereiniger, können die Erfassung dieser Objekte optimieren, sodass die Anwendung nicht zu oft unterbrochen wird. Der Android Garbage Collector ist leider nicht in der Lage, solche Optimierungen durchzuführen, und die Erstellung kurzlebiger Objekte in leistungskritischen Codepfaden ist daher für Ihre Anwendung sehr kostspielig.

Nach meinem Verständnis besteht also keine dringende Notwendigkeit, den GC anzurufen. Es ist besser, mehr Aufwand zu betreiben, um das unnötige Erstellen von Objekten zu vermeiden (wie das Erstellen von Objekten in Schleifen).

19
Andreas_D

Meine App verwaltet viele Bilder und ist mit einem OutOfMemoryError abgestorben. Das hat mir geholfen. In der Manifest.xml hinzufügen

<application
....
   Android:largeHeap="true"> 
7
Klykoo

Es scheint, dass System.gc() nicht auf Art Android 6.0.1 Nexus 5x, also verwende ich stattdessen Runtime.getRuntime().gc();.

7
cmicat

Im Allgemeinen sollten Sie GC nicht explizit mit System.gc () aufrufen. Es gibt sogar die Vorlesung IO= ( http://www.youtube.com/watch?v=_CruQY55HOk ), in der erklärt wird, was das Protokoll für die GC-Pausen bedeutet Sie geben auch an, niemals System.gc () aufzurufen, da Dalvik besser als Sie weiß, wann dies zu tun ist.

Andererseits ist, wie oben erwähnt, der GC-Prozess in Android (wie alles andere auch) manchmal fehlerhaft. Dies bedeutet, dass Dalvik-GC-Algorithmen nicht mit Hotspot- oder JRockit-JVMs vergleichbar sind und möglicherweise Probleme verursachen Eine dieser Situationen ist das Zuweisen von Bitmap-Objekten. Dies ist schwierig, da Heap- und Nicht-Heap-Speicher verwendet werden und eine lose Instanz eines Bitmap-Objekts auf einem speicherbeschränkten Gerät ausreicht, um eine OutOfMemory-Ausnahme auszulösen Der Aufruf, nachdem Sie diese Bitmap nicht mehr benötigen, wird in der Regel von vielen Entwicklern vorgeschlagen und wird von manchen sogar als bewährte Methode angesehen.

Bessere Praxis ist die Verwendung von .recycle () für eine Bitmap, da diese Methode den systemeigenen Speicher der Bitmap als sicher zum Löschen kennzeichnet. Beachten Sie, dass dies sehr versionsabhängig ist, was bedeutet, dass es in der Regel für ältere Android Versionen (glaube ich vor 3.0) erforderlich ist, aber für spätere Versionen nicht erforderlich ist. Außerdem wird es nicht schaden Ich benutze es häufig auf neueren Ether-Versionen (mach das einfach nicht in einer Schleife oder so ähnlich.) Die neue ART-Laufzeit hat sich sehr verändert, weil sie eine spezielle Heap- "Partition" für große Objekte eingeführt haben, aber ich denke, es wird nicht viel schaden mach das mit ART ether.

Auch ein sehr wichtiger Hinweis zu System.gc (). Diese Methode ist kein Befehl, zu dessen Beantwortung Dalvik (oder JVMs) verpflichtet sind. Betrachten Sie es eher so, als würden Sie der virtuellen Maschine sagen: "Könnten Sie bitte die Müllabfuhr durchführen, wenn es kein Ärger ist?".

6
PSIXO

Der beste Weg, um OOM während der Erstellung von Bitmaps zu vermeiden.

http://developer.Android.com/training/displaying-bitmaps/index.html

3
prabhu

Es ist nicht erforderlich, den Garbage Collector nach einem OutOfMemoryError aufzurufen.

Es ist Javadoc klar heißt:

Thrown when the Java Virtual Machine cannot allocate an object because it is out of memory, and no more memory could be made available by the garbage collector.

Daher hat der Garbage Collector bereits versucht, Speicher freizugeben, bevor der Fehler generiert wurde, war jedoch nicht erfolgreich.

2
perdian

Ich würde nein sagen, weil die Entwicklerdokumentation über RAM Nutzung Zustand:

...
GC_EXPLICIT

Ein expliziter GC, zum Beispiel, wenn Sie gc () (welches sollten Sie meiden aufrufen und vertraue stattdessen darauf, dass der GC bei Bedarf ausgeführt wird.

...

Ich habe den relevanten Teil fett hervorgehoben.

Schauen Sie sich die YouTube-Serie an, Android Performance Patterns - sie zeigt Ihnen Tipps zum Verwalten der Speichernutzung Ihrer App (z. B. mithilfe von ArrayMaps und SparseArrays von Android anstelle von HashMaps).

Kurznotiz für Xamarin-Entwickler.

Wenn Sie in Xamarin.Android-Apps System.gc() aufrufen möchten, sollten Sie Java.Lang.JavaSystem.Gc() aufrufen.

2
Denis Gordin