Ich versuche, eine große CSV-Datei (ca. 6 GB) in Pandas zu lesen, und es wird ein Speicherfehler angezeigt:
MemoryError Traceback (most recent call last)
<ipython-input-58-67a72687871b> in <module>()
----> 1 data=pd.read_csv('aphro.csv',sep=';')
...
MemoryError:
Hilfe dazu?
Antworten:
Der Fehler zeigt, dass der Computer nicht über genügend Speicher verfügt, um die gesamte CSV gleichzeitig in einen DataFrame einzulesen. Angenommen, Sie benötigen nicht den gesamten Datensatz auf einmal im Speicher. Eine Möglichkeit, das Problem zu vermeiden, besteht darin , die CSV in Blöcken zu verarbeiten (durch Angabe des
chunksize
Parameters):Der
chunksize
Parameter gibt die Anzahl der Zeilen pro Block an. (Der letzte Block kannchunksize
natürlich weniger als Zeilen enthalten .)quelle
DF.append(chunk)
innerhalb der Schleife auf. Das wirdO(N^2)
Kopiervorgänge verwenden. Es ist besser, die aggregierten Daten an eine Liste anzuhängen und dann den DataFrame aus der Liste mit einem Aufruf vonpd.DataFrame
oderpd.concat
(abhängig vom Typ der aggregierten Daten) zu erstellen.DF.append(chunk)
in einer Schleife erfordertO(N^2)
Kopiervorgänge mitN
der Größe der Chunks, da bei jedem AufrufDF.append
ein neuer DataFrame zurückgegeben wird. Durch Aufrufenpd.DataFrame
oderpd.concat
einmal außerhalb der Schleife wird der Kopieraufwand verringertO(N)
.chunksize
Parameter bezieht sich auf die Anzahl der Zeilen pro Block. Der letzte Block kannchunksize
natürlich weniger als Zeilen enthalten .pd.concat([list_of_dfs])
einmal nach der Schleife ist viel schneller als Aufrufpd.concat
oderdf.append
mehrmals in der Schleife. Natürlich benötigen Sie eine beträchtliche Menge an Speicher, um die gesamte 6-GB-CSV als einen DataFrame zu speichern.Chunking sollte nicht immer die erste Anlaufstelle für dieses Problem sein.
Ist die Datei aufgrund wiederholter nicht numerischer Daten oder unerwünschter Spalten groß?
In diesem Fall können Sie manchmal massive Speichereinsparungen feststellen, indem Sie Spalten als Kategorien einlesen und die erforderlichen Spalten über den
usecols
Parameter pd.read_csv auswählen .Erfordert Ihr Workflow das Schneiden, Bearbeiten und Exportieren?
In diesem Fall können Sie dask.dataframe verwenden , um zu schneiden, Ihre Berechnungen durchzuführen und iterativ zu exportieren. Das Chunking wird stillschweigend von dask ausgeführt, das auch eine Teilmenge der Pandas-API unterstützt.
Wenn alles andere fehlschlägt, lesen Sie Zeile für Zeile über Chunks.
Chunk via Pandas oder via CSV-Bibliothek als letztes Mittel.
quelle
Ich ging so vor:
quelle
read_csv
zuread_table
?Für große Datenmengen empfehle ich die Verwendung der Bibliothek "dask",
z.
Weitere Informationen finden Sie hier in der Dokumentation .
Eine weitere gute Alternative wäre die Verwendung von Modin, da alle Funktionen mit Pandas identisch sind, jedoch verteilte Datenrahmenbibliotheken wie dask genutzt werden.
quelle
Die obige Antwort erfüllt das Thema bereits. Wenn Sie alle Daten im Speicher benötigen, schauen Sie sich bcolz an . Es komprimiert die Daten im Speicher. Ich habe wirklich gute Erfahrungen damit gemacht. Aber es fehlen viele Pandas-Funktionen
Bearbeiten: Ich habe Komprimierungsraten bei etwa 1/10 oder Originalgröße, denke ich, natürlich abhängig von der Art der Daten. Wichtige fehlende Merkmale waren Aggregate.
quelle
chunks
genannten Methode vorverarbeiten und dann bcolz verwenden, wenn Sie alle Daten im Speicher benötigen, um eine Analyse durchzuführen. Nur ein Gedanke.Sie können die Daten als Chunks einlesen und jeden Chunk als Pickle speichern.
Im nächsten Schritt lesen Sie die Gurken ein und hängen jede Gurke an Ihren gewünschten Datenrahmen an.
quelle
df
vollständig in den Speicher passt (wie impliziert) und dieselbe Datenmenge wie Ihre Eingabe enthält, müssen Sie sicher überhaupt keinen Block erstellen?Die Funktionen read_csv und read_table sind nahezu identisch. Sie müssen jedoch das Trennzeichen "," zuweisen, wenn Sie die Funktion read_table in Ihrem Programm verwenden.
quelle
Lösung 1:
Verwenden von Pandas mit großen Datenmengen
Lösung 2:
quelle
dfList.append
, verarbeite einfach jeden chunk (df
) separatHier folgt ein Beispiel:
quelle
Sie können sframe ausprobieren, das dieselbe Syntax wie pandas hat, aber Sie können Dateien bearbeiten, die größer als Ihr RAM sind.
quelle
Wenn Sie Pandas verwenden, lesen Sie eine große Datei in Chunk und geben Sie dann Zeile für Zeile nach. Hier ist, was ich getan habe
quelle
Ich möchte eine umfassendere Antwort geben, die auf den meisten potenziellen Lösungen basiert, die bereits bereitgestellt werden. Ich möchte auch auf eine weitere mögliche Hilfe hinweisen, die den Lesevorgang unterstützen kann.
Option 1: dtypes
"dtypes" ist ein ziemlich leistungsfähiger Parameter, mit dem Sie den Speicherdruck von
read
Methoden reduzieren können. Siehe diese und diese Antwort. Pandas versuchen standardmäßig, d-Typen der Daten abzuleiten.Bezugnehmend auf Datenstrukturen findet für alle gespeicherten Daten eine Speicherzuordnung statt. Grundsätzlich beziehen Sie sich auf die folgenden Werte (Die folgende Tabelle zeigt Werte für die Programmiersprache C):
Auf dieser Seite finden Sie die Übereinstimmung zwischen den Typen NumPy und C.
Angenommen, Sie haben eine Reihe von Ganzzahlen mit Ziffern . Sie können sowohl theoretisch als auch praktisch ein Array vom Typ 16-Bit-Ganzzahl zuweisen, aber Sie würden dann mehr Speicher zuweisen, als Sie tatsächlich zum Speichern dieses Arrays benötigen. Um dies zu verhindern, können Sie die
dtype
Option aktivierenread_csv
. Sie möchten die Array-Elemente nicht als lange Ganzzahl speichern, wo Sie sie tatsächlich mit einer 8-Bit-Ganzzahl (np.int8
odernp.uint8
) versehen können.Beachten Sie die folgende dtype-Karte.
Quelle: https://pbpython.com/pandas_dtypes.html
Sie können
dtype
Parameter als Parameter für Pandas-Methoden übergeben,read
wie dies unter {column: type} vorgeschrieben ist.Option 2: Von Chunks gelesen
Durch das Lesen der Daten in Blöcken können Sie auf einen Teil der Daten im Speicher zugreifen, und Sie können eine Vorverarbeitung auf Ihre Daten anwenden und die verarbeiteten Daten anstelle von Rohdaten beibehalten. Es wäre viel besser, wenn Sie diese Option mit der ersten Option, dtypes , kombinieren würden .
Ich möchte auf die Pandas-Kochbuchabschnitte für diesen Prozess hinweisen, die Sie hier finden . Beachten Sie diese beiden Abschnitte dort;
Option 3: Dask
Dask ist ein Framework, das auf der Dask-Website wie folgt definiert ist :
Es wurde geboren, um die notwendigen Teile abzudecken, die Pandas nicht erreichen können. Dask ist ein leistungsstarkes Framework, mit dem Sie viel mehr auf Daten zugreifen können, indem Sie es auf verteilte Weise verarbeiten.
Sie können dask verwenden, um Ihre Daten als Ganzes vorzuverarbeiten. Dask kümmert sich um den Chunking-Teil. Im Gegensatz zu Pandas können Sie also einfach Ihre Verarbeitungsschritte definieren und Dask die Arbeit erledigen lassen. Dask wendet die Berechnungen nicht an, bevor sie explizit von
compute
und / oder gepusht werdenpersist
(siehe die Antwort hier für den Unterschied).Andere Hilfsmittel (Ideen)
quelle
Zusätzlich zu den obigen Antworten ist d6tstack eine weitere gute Option für diejenigen, die CSV verarbeiten und dann nach CSV, Parkett oder SQL exportieren möchten . Sie können mehrere Dateien laden und es werden Datenschemaänderungen (hinzugefügte / entfernte Spalten) behandelt. Chunked out of Core-Unterstützung ist bereits eingebaut.
quelle
Für den Fall, dass noch jemand nach so etwas sucht, habe ich festgestellt, dass diese neue Bibliothek namens modin helfen kann. Es verwendet verteiltes Computing, das beim Lesen helfen kann. Hier ist ein schöner Artikel , der seine Funktionalität mit Pandas vergleicht. Es verwendet im Wesentlichen die gleichen Funktionen wie Pandas.
quelle
modin
mit dem etablierten verglichen wirddask.dataframe
? Siehe beispielsweise Wechsel von Pandas zu Dask, um alle lokalen CPU-Kerne zu nutzen .Bevor Sie die Option chunksize verwenden möchten, können Sie einfach die Option nrows verwenden, wenn Sie sicher sein möchten, welche Prozessfunktion Sie in die von @unutbu erwähnte Chunking-for-Schleife schreiben möchten.
Sobald Sie sicher sind, dass der Prozessblock bereit ist, können Sie ihn in die Chunking-for-Schleife für den gesamten Datenrahmen einfügen.
quelle