Frage

Ich erhalte eine Java OutOfMemoryError, wenn ich diese Methode aufrufen - ich verwende es in einer Schleife viele große Dateien nacheinander zu analysieren. meine Vermutung ist, dass result.toString() nicht Müll ordnungsgemäß während der Schleife immer gesammelt. wenn ja, wie soll ich das Problem beheben?

private String matchHelper(String buffer, String regex, String method){
    Pattern abbrev_p = Pattern.compile(regex);//norms U.S.A., B.S., PH.D, PH.D.
    Matcher abbrev_matcher = abbrev_p.matcher(buffer);
    StringBuffer result = new StringBuffer();
    while (abbrev_matcher.find()){
            abbrev_matcher.appendReplacement(result, abbrevHelper(abbrev_matcher));
    }
    abbrev_matcher.appendTail(result);
    String tempResult = result.toString(); //ERROR OCCURS HERE
  return tempResult;

}
War es hilfreich?

Lösung

auf diese Weise geschrieben werden, müssen Sie grob 6 Byte Speicher für jedes Zeichen in der Datei.

Jedes Zeichen ist zwei Bytes. Sie haben den Roh-Eingang, die ersetzt Ausgabe (im Puffer), und Sie sind für eine dritte Kopie zu fragen, wenn Sie genügend Speicherplatz aus.

Wenn die Datei in so etwas wie ASCII oder ISO-8859-1 (eine Single-Byte-Zeichencodierung) codiert ist, das heißt es wird sechs Mal im Speicher größer sein als auf dem Datenträger.

Sie können mehr Speicher für den Prozess zuweisen, aber eine bessere Lösung könnte den Eingang „Strömungs“ -Lesen, Scan zu verarbeiten sein, und schreiben Sie die Daten ohne Laden sie alle in dem Speicher auf einmal.

Andere Tipps

Wenn Sie Ihre Dateien alle sehr groß sind, verarbeitet werden, sagen mehr als ein paar hundert MB, dann sollten Sie wirklich gehen mit Strom Verarbeitung statt dieser „alle in den Speicher geladen“ Art und Weise, wie @erickson vorgeschlagen.

Ansonsten gibt es ein paar Dinge, die Sie könnten versuchen, alle Speicherverbrauch so weit wie möglich zu reduzieren:

  1. Versuchen Sie richtig vergrößern Ihre Heap-Größe, wenn noch nicht (wenn zutreffend).
  2. Give StringBuffer eine Anfangsgröße gleich der Länge des gegebenen String buffer. Dies sollte den unnötigen Speicherverbrauch reduzieren, während die StringBuffer im Prozess erweitert. Ich nehme an, es wird nur bestimmte Worte der ursprünglichen Zeichenfolge zu ersetzen und soll die gleiche Länge mehr oder weniger sein.
  3. Wenn möglich, vielleicht könnten Sie das generierte StringBuffer Objekt zurückgeben statt. Der Aufruf seine toString() erst nach dem ursprünglichen String Objekt loszuwerden.

rechne ich das Problem mit StringBuilder.append(). Wenn Matcher anhängen Folge von Zeichen auf den Builder.

Wie im Artikel über OutOfMemoryError mit String / String ist es ein bekanntes Problem, dass append (), um die Kapazität, wenn interne Puffer chars verdoppeln, wenn die Kapazität nicht ausreicht. Gehen Sie für Ströme wie Erickson vorgeschlagen.

Ich stimme mit den anderen Antworten ... aber ... einfach, weil die Ausnahme tritt nicht unbedingt bedeutet es das Problem. Sie können sehr gut undichte Speicher anderswo und das geschieht genau der richtige Ort zu sein, dass es aufgedeckt wird. Sie sollten einen Profiler laufen die Speichernutzung zu untersuchen und überprüfen, genau das, was Objekte werden nicht gesammelt werden.

Ja! Puffer nicht anders in Erinnerung werden laufen Sie es speziell, wenn Sie über 2 MB auf I gehst / O.

Empfehlenswerter Link zum Fixieren und Anhängen Text: http: // java.ittoolbox.com/documents/appending-data-to-a-file-18786

Sie könnten versuchen, ein StringBuffer Rückkehr und es null nach dem Gebrauch zu setzen.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top