Python wird getötet (wahrscheinlich Speicherleck)

8

Ich habe seit ein paar Wochen daran gearbeitet und ich habe viele Fragen über Python Memory Leak gelesen, aber ich kann es einfach nicht herausfinden.

Ich habe eine Datei, die ungefähr 7 Millionen Zeilen enthält. Für jede Zeile muss ich ein Wörterbuch erstellen. Das ist also eine Wörterbuchliste, die wie folgt aussieht:

%Vor%

Was ich mache ist ...

%Vor%

Das Problem ist, dass wenn ich das starte, es immer um die 6000000ste Linie herum getötet wird. Ursprünglich habe ich nur dict = {} gemacht, aber ich habe dict.clear () geändert, nachdem ich ähnliche Beiträge gelesen hatte, aber es hat nichts verbessert. Ich kenne einige Artikel, die über Zirkelverweise erwähnt wurden, und ich habe mir meinen Code angesehen, aber ich dachte nicht, dass ich dieses Problem habe.

Ich bezweifle, dass das Speichern von 7 Millionen Wörterbüchern in einer Liste in Python nicht behandelt werden kann? Ich würde mich über jeden Rat freuen, wie ich die ganzen Dinge ausführen kann, ohne getötet zu werden.

(Die Version ist 2.7.4)

    
kabichan 20.07.2013, 19:57
quelle

2 Antworten

8

Versuchen Sie:

%Vor%

Ich glaube, das ist es, was Sie mit Ihrem Code erreichen wollen.

Dies vermeidet, dass .readlines() zuerst die Datei in den Speicher lädt, verwendet Counter , um die Zählung durchzuführen, und erstellt die Liste auf einmal, ohne um Leerzeichen zu blättern / Wörter zuzuweisen / löschen / an Listen anfügen ...

    
Jon Clements 20.07.2013, 20:04
quelle
1

Es gibt keine Möglichkeit, ein Speicherleck mit einem so einfachen Codeschnipsel zu haben, weil Python mindestens halbwegs brauchbare Garbage Collection verwendet. Ein potentielles Problem ist, dass Ihnen der Speicher ausgeht (vermeiden Sie definitiv .readlines für Starter; verwenden Sie stattdessen "for line in my_file"); Außerdem verwendet ein Wörterbuch aus verschiedenen Gründen eine ganze Menge Speicher - zum Beispiel, dass ein Wörterbuch absichtlich eine Hashtabelle verwendet, die erheblich größer ist als die aktuelle Schlüsselmenge, um Kollisionen zu vermeiden, aber auch schnell viel hinzuzufügen bei Bedarf neue Schlüssel, mit amortisierter O (1) Zeit pro Einfügung. Da Sie sich dem Ende Ihrer Datei nähern, bevor sie stirbt, können Sie Ihr endgültiges Diktat als 2-Tupel von k-Tupeln speichern, wobei das erste k-Tupel die k-Schlüssel enthält, die Sie speichern möchten , und das zweite k-Tupel ist Ihr k zählt für die k-Tasten. Dies sollte etwas Speicher sparen, mit dem Aufwand, dass, um ein Nachschlagen von my_key in einem Ihrer 2-Tupel T zu tun, Sie etwas tun müssen wie:

%Vor%

Die Laufzeit für eine Suche ist linear in der Anzahl der Schlüssel, die Sie durchsuchen müssen, anstelle der konstanten Zeit (obwohl beachten Sie, dass Hashing, um eine Wörterbuchsuche zu tun, keine triviale Operation ist, so dass die Konstante ist größer als eine typische Konstante für eine einfachere Operation). Wenn Sie Ihre Schlüssel in sortierter Reihenfolge gespeichert haben, könnten Sie die binäre Suche verwenden, um Ihren Schlüssel schnell zu finden, aber das würde mehr Code erfordern, und ich gehe davon aus, dass Sie Python teilweise verwenden, weil es dazu neigt, kurzen Code zu geben. Wenn Sie jedoch bereits 6 Millionen Wörterbücher erfolgreich erstellen, dürfen Ihre 7 Millionen Wörterbücher im Durchschnitt nicht viele Schlüssel enthalten. Wenn Sie also wirklich Python für Ihren Datensatz verwenden möchten, ist dies möglicherweise eine der wenigen Möglichkeiten, bis Sie eine Maschine mit mehr Speicher erhalten.

    
user2566092 20.07.2013 20:42
quelle

Tags und Links