.NET Out of Memory-Ausnahme - Verwendet 1,3 GB, aber 16 GB installiert


91

Ich erhalte in meiner c # -Anwendung eine Ausnahme wegen Speichermangel, wenn die Speichernutzung für die Anwendung etwa 1,3 GB überschreitet.

Ich hatte das gleiche Problem auf einem 32-Bit-Computer mit 3 GB Speicher und es war damals sinnvoll, aber jetzt habe ich die Hardware auf einen 64-Bit-Computer mit 16 GB Speicher mit High-End-Motherboard und RAM, aber nicht genügend Speicher aktualisiert Ausnahme tritt immer noch nach 1,3 GB auf!

Ich weiß, dass es keine einzelnen Objekte über 2 GB gibt und 1,3 ohnehin weniger als 2 GB, so dass die eingebaute MS 2 GB-Grenze für ein einzelnes Objekt wahrscheinlich nicht das Problem ist ...

Es scheint, als gäbe es einen Windows-Kill-Switch, wenn eine App einen bestimmten Schwellenwert für die Speichernutzung erreicht ... Dann sollte es vielleicht eine Möglichkeit geben, dies in der Registrierung zu konfigurieren.

Jede Hilfe wird sehr geschätzt!


9
Ist Ihr OS 64bit auch?
fge

9
Selbst wenn Ihr Betriebssystem 64-Bit ist, stellen Sie sicher, dass Ihr Prozess auch 64-Bit (oder AnyCPU) ist
Knowleech

Antworten:


90

Es gibt keinen Unterschied, bis Sie mit derselben Zielarchitektur kompilieren . Ich nehme an, Sie kompilieren 32in beiden Fällen für die Bit-Architektur.

Es ist erwähnenswert, dass OutOfMemoryExceptiondies auch ausgelöst werden kann, wenn Sie 2GBSpeicher erhalten, der von einer einzelnen Sammlung in CLR (z. B. List<T>) sowohl auf Architekturen 32als auch auf 64Bit zugewiesen wird .

Um von der Speichergüte der Bitarchitektur profitieren zu können 64, müssen Sie Ihre Code-Targeting- Bitarchitektur kompilieren64 . Danach läuft Ihre Binärdatei natürlich nur noch auf 64Bit, profitiert jedoch von der Möglichkeit, dass mehr Speicherplatz im RAM verfügbar ist.


8
Was ist mit AnyCPU?
dtb

1
Ja, AnyCPU ist auch eine Option, bei der Sie eine Option für JIT-Architektur-abhängigen Code haben. Die Ausrichtung auf eine bestimmte Architektur kann jedoch weiterhin von Vorteil sein, wenn Sie nicht über (beispielsweise) Ressourcen verfügen. Ich habe keine Ahnung, worum es in der Architektur von OP geht.
Tigran

4
Ich wusste das :) - Danke Tigran, ich habe die Lösung in x64 neu erstellt und die Ausnahme ist verschwunden.
Paceman

63

Wie bereits erwähnt, steht Ihnen beim Kompilieren der App in x64 viel mehr Speicher zur Verfügung.

Für den Fall, dass eine App in x86 erstellt werden muss, gibt es eine Möglichkeit, das Speicherlimit von 1,2 GB auf 4 GB zu erhöhen (dies ist das tatsächliche Limit für 32-Bit-Prozesse):

Im VC / bin-Ordner des Visual Studio-Installationsverzeichnisses muss sich eine editbin.exeDatei befinden. In meiner Standardinstallation finde ich es also unter

C:\Program Files (x86)\Microsoft Visual Studio 10.0\VC\bin\editbin.exe

Damit das Programm funktioniert, müssen Sie es möglicherweise zuerst vcvars32.batim selben Verzeichnis ausführen . Dann ein

editbin /LARGEADDRESSAWARE <your compiled exe file>

reicht aus, um Ihr Programm 4 GB RAM verwenden zu lassen. <your compiled exe file>ist die exe, die VS beim Kompilieren Ihres Projekts generiert hat.

Wenn Sie dieses Verhalten jedes Mal automatisieren möchten, wenn Sie Ihr Projekt kompilieren, verwenden Sie das folgende Post-Build-Ereignis für das ausgeführte Projekt:

if exist "$(DevEnvDir)..\tools\vsvars32.bat" (
   call "$(DevEnvDir)..\tools\vsvars32.bat"
   editbin /largeaddressaware "$(TargetPath)"
)

Nebenbemerkung: Dasselbe kann mit dem gemacht werden devenv.exe, damit Visual Studio auch 4 GB RAM anstelle von 1,2 GB verwendet (aber zuerst das alte sichern devenv.exe).


Vielen Dank. Das funktioniert bei mir. Haben wir jedoch Probleme festgestellt, nachdem das Speicherlimit auf 4 GB erhöht wurde?
Maverick

28

Erwähnenswert ist, dass die Standardeinstellung für eine Kompilierung "Beliebige CPU" jetzt das Kontrollkästchen "32-Bit bevorzugen" aktiviert. Wenn auf AnyCPU eingestellt ist, kann auf einem 64-Bit-Betriebssystem mit 16 GB RAM bei 2 GB immer noch eine Ausnahme wegen Speichermangel auftreten, wenn dies aktiviert ist.

Prefer32BitCheckBox


2
Dies löste meine Probleme mit dem Speichermangel absolut und ersparte uns eine
Menge

2

Es sieht so aus, als hätten Sie einen 64-Bit-Bogen, aber eine 32-Bit-Version der .NET-Laufzeit und / oder eine 32-Bit-Version von Windows.

Daher ist der für Ihren Prozess verfügbare Adressraum immer noch derselbe. Er hat sich gegenüber dem vorherigen Setup nicht geändert.

Upgrade auf ein 64-Bit-Betriebssystem und eine 64-Bit-.NET-Version;)


1

Läuft Ihre Anwendung als 64- oder 32-Bit-Prozess? Sie können dies im Task-Manager überprüfen.

Es könnte sein, dass es mit 32 Bit läuft, obwohl das gesamte System mit 64 Bit läuft.

Bei 32 Bit kann dies durch eine Bibliothek eines Drittanbieters verursacht werden. Stellen Sie jedoch zunächst sicher, dass Ihre Anwendung für "Beliebige CPU" kompiliert wird, wie in den Kommentaren angegeben.


0

Wenn Sie 32-Bit-Windows haben, funktioniert diese Methode nicht ohne die folgenden Einstellungen.

  1. Führen Sie die Eingabeaufforderung cmd.exe aus (wichtig: Als Administrator ausführen).
  2. Geben Sie bcdedit.exe ein und führen Sie es aus
  3. Schauen Sie sich die "erhöhenuserva" -Parameter an und es gibt keine folgende Anweisung
  4. bcdedit / set raiseuserva 3072
  5. und erneut Schritt 2 und überprüfen Sie die Parameter

Wir haben diese Einstellungen hinzugefügt und dieser Block gestartet.

if exist "$(DevEnvDir)..\tools\vsvars32.bat" (
   call "$(DevEnvDir)..\tools\vsvars32.bat"
   editbin /largeaddressaware "$(TargetPath)"
)

Weitere Informationen - Befehl increaseuserva: https://docs.microsoft.com/en-us/windows-hardware/drivers/devtest/bcdedit--set

Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.