Wann beschließt GC, Generation 2 zu sammeln?

8

Während des Tages sehe ich viele Gen 2 Sammlungen in unserem Windows-Dienst.

Wann beschließt GC, die vollständige Sammlung vorzunehmen, anstatt nur Gen1 und Gen0 oder nur Gen0 zu sammeln?

    
Piotr Perak 20.12.2011, 21:14
quelle

2 Antworten

9

Lesen Sie Ссылка und die verlinkten Artikel für weitere Informationen. Im Allgemeinen wird gen2 "wenn nötig" gesammelt.

Eine Sache, die übermäßige Gen2-Sammlungen verursachen kann, ist der Large Object Heap (LOH). Wenn der LOH gefüllt wird, wird eine vollständige Sammlung ausgelöst. Wenn Ihre Anwendung viele große Objekte (80K oder größer) zuweist und freigibt, könnte das Ihr Problem sein.

Siehe CLR Inside Out: Großer Objekt-Haufen aufgedeckt .

Ziehen Sie auch die Verwendung des Server-Garbage-Collectors in Ihrem Dienst in Betracht. Es bietet normalerweise eine bessere Leistung (weniger Sammlungen). Fügen Sie dies Ihrer app.config-Datei hinzu:

%Vor%     
Jim Mischel 20.12.2011, 21:31
quelle
5

Im Allgemeinen wird eine Sammlung ausgelöst (unter jeder Generation), wenn eine der folgenden Bedingungen erfüllt ist:

  • Die Zuweisung überschreitet den Schwellenwert. Ich erinnere mich vage daran, dass dies dynamisch ist, basierend auf den aktuellen Bedürfnissen. Kann jemand bestätigen / ablehnen?
  • Es gibt eine Situation mit wenig Speicher
  • Es wird über GC.Collect ()
  • aufgerufen

Es kann ein anderes Szenario geben, das ich vermisse, aber das ist es im Allgemeinen. Der erste ist das, was normalerweise eine Sammlung startet, und wenn man davon ausgeht, dass es (relativ) teurer ist, G2 zu sammeln, als G0, sieht man weniger davon.

Um die Frage im Kommentar zu beantworten:
Jede Generation hat einen Schwellenwert, der beim Treffer eine Sammlung auslöst. Gen0 könnte 5mb sein und wird ausgelöst, wenn das gefüllt ist. Nach GC läuft, wenn Sie noch 5mb drin haben, glaube ich, dass es das Limit erhöhen wird. Wenn dies nicht der Fall ist, löst jede Zuweisung eine Sammlung aus und Sie haben ein Problem. Gen2 könnte 20mb sein (beachte, dass ich hier Zahlen erfinde) und die gleiche Logik gilt dort.

Betrachten wir als Beispiel für ein Lehrbuch ein einfaches Szenario.

  1. Neue app-allokierte Objekte und all werden bei Gen0 für insgesamt 3 MB an Daten platziert. (Dies ist nicht immer der Fall, aber so tun, als wäre es)
  2. Ein GC-Treffer und 1 MB davon werden nach G1 verschoben, der Rest wird aufgeräumt.
  3. G0 ist jetzt frei und G1 hat 1MB drin.
  4. Es werden mehr Objekte erstellt und mehr GCs passieren. Nach einer Weile wird G1 voll und einige werden nach G2 verschoben.
  5. Objekte bleiben dort, bis G2 voll ist, und dann werden sie bereinigt, wenn sie nicht verwendet werden . Wenn auf ein Objekt immer noch verwiesen wird, bleibt es in G2, bis es gereinigt werden kann .

Eine vollständige GC ist teuer, und ich habe Tage verstreichen sehen, ohne dass es passiert ist. Zugegeben, das war auf einem System mit 64 GB Ram verfügbar, und es gab keine Notwendigkeit dafür.

    
Joe 20.12.2011 21:30
quelle

Tags und Links