2014-11-23 8 views
5

Ich bin eine shelve Datei von Sequenzen aus einer genomischen FASTA-Datei zu erstellen:Shelve Wörterbuch Größe> 100Gb für eine 2Gb Textdatei

# Import necessary libraries 
import shelve 
from Bio import SeqIO 

# Create dictionary of genomic sequences 
genome = {} 
with open("Mus_musculus.GRCm38.dna.primary_assembly.fa") as handle: 
    for record in SeqIO.parse(handle, "fasta"): 
     genome[str(record.id)] = str(record.seq) 

# Shelve genome sequences 
myShelve = shelve.open("Mus_musculus.GRCm38.dna.primary_assembly.db") 
myShelve.update(genome) 
myShelve.close() 

Die Datei selbst 2,6 GB ist, aber wenn ich versuche, und ad acta es, eine Datei von> 100 GB wird produziert, und mein Computer wird eine Reihe von Beschwerden über den Mangel an Arbeitsspeicher und die Startdiskette, die voll ist, werfen. Dies scheint nur zu passieren, wenn ich versuche, dies unter OSX Yosemite zu starten, auf Ubuntu funktioniert es wie erwartet. Irgendwelche Vorschläge, warum das nicht funktioniert? Ich benutze Python 3.4.2

+0

Welche Python-Versionen verwenden Sie? – Daniel

+0

@Daniel Python 3.4.2 – jma1991

+0

Darf mit diesem verwandt sein? http://stackoverflow.com/questions/26574954/virtualenv-fails-on-os-x-yosemite-with-oserror – Ashalynd

Antwort

2

Überprüfen, welche Schnittstelle für dbm verwendet wird von import dbm; print(dbm.whichdb('your_file.db') Das Dateiformat von shelve hängt von der am besten installierten binären Paket auf Ihrem System und seinen Schnittstellen. Das neueste ist gdbm, während dumb eine Ausweichlösung ist, wenn keine Binärdatei gefunden wird, ndbm ist etwas dazwischen.
https://docs.python.org/3/library/shelve.html
https://docs.python.org/3/library/dbm.html

Es ist nicht günstig, alle Daten im Speicher zu haben, wenn Sie den gesamten Speicher für Dateisystem-Cache verlieren. Aktualisieren durch kleinere Blöcke ist besser. Ich sehe sogar keine Verlangsamung, wenn Artikel einzeln aktualisiert werden.

myShelve = shelve.open("Mus_musculus.GRCm38.dna.primary_assembly.db") 
with open("Mus_musculus.GRCm38.dna.primary_assembly.fa") as handle: 
    for i, record in enumerate(SeqIO.parse(handle, "fasta")): 
     myShelve.update([(str(record.id), str(record.seq))]) 
myShelve.close() 

Es ist bekannt, dass dbm Datenbanken fragmentiert wurde, wenn die App nach Updates ohne Datenbank close Aufruf fiel. Ich denke, das war dein Fall. Jetzt haben Sie wahrscheinlich noch keine wichtigen Daten in der großen Datei, aber in Zukunft können Sie eine Datenbank durch gdbm.reorganize() defragmentieren.

0

Ich hatte das gleiche Problem: Auf einem macOS System mit einem Regal mit etwa 4 Megabytes von Daten wuchs die enorme Größe von 29 Gigabytes auf der Festplatte! Dies ist offensichtlich passiert, weil ich die gleichen Schlüsselwertpaare im Regal immer und immer wieder aktualisiert habe.

Als mein shelve auf GNU dbm beruhte war ich in der Lage seinen Hinweis zu nutzen, um neu zu organisieren. Hier ist der Code, meine shelve Datei wieder auf die normale Größe innerhalb von Sekunden gebracht:

import dbm 
db = dbm.open(shelfFileName, 'w') 
db.reorganize() 
db.close() 

Ich bin nicht sicher, ob diese Technik für andere (nicht GNU) funktionieren dbms auch. Um Ihre dbm System zu testen, denken Sie daran, den Code von @hynekcer gezeigt:

import dbm 
print(dbm.whichdb(shelfFileName)) 

Wenn GNU dbm von Ihrem System benutzt wird, sollte dies Ausgang ‚dbm.gnu‘ (das ist der neue Name für die ältere gdbm ist).

Verwandte Themen