2016-07-30 8 views
1

--- EDIT 2 --- So bekomme ich die Frage, warum ich die Wörterbücher verwenden ?, diese Frage ist ein auf Follow-up dieser: csv file compression without using existing libraries in PythonIterate in 2 verschiedene Wörterbücher gleichzeitig in Python

I Need to komprimieren, um ein 500k csv-Datei (19 MB), und ich wählte Wörterbuch verwenden, um die Zecken in einer cSV-Datei und symbs in eine andere speichern zu können, um die Werte dekomprimieren

FRAGE: Wie iterieren ich die optimierte Art und Weise ? Dies ist nur ein Beispiel für 4 Zeilen, aber meine reale Datei hat 500 000 Zeilen und führt mich immer wieder durch die Liste.

Ich habe 3 Wörterbücher:

originalDict = { 
       0: ['6NH8', 'F', 'A', '0', '60541567', '60541567', '78.78', '20'], 
       1: ['6NH8', 'F', 'A', '0', '60541569', '60541569', '78.78', '25'], 
       2: ['6AH8', 'F', 'B', '0', '60541765', '60541765', '90.52', '1'], 
       3: ['QMH8', 'F', 'B', '0', '60437395', '60437395', '950.5', '1'] 
       } 
ticks = {0: '6NH8', 1: '6AH8', 2: 'QMH8'} 
symbs = {0: 'F,A', 1: 'F,B'} 

ich durch originalDict iterieren wollen und die "Ticks" ändern und dann die symbs bei index 1 und index 2 und entfernen Sie dann index 2

so, also

0: ['6NH8', 'F', 'A', '0', '60541567', '60541567', '78.78', '20'] 

wird:

[0, '0', '0', '60541567', '60541567', '78.78', '20'] 

Ich habe eine Zeit für eine Schleife durch Werte in originalDict gehen, und im Inneren, dass eine andere for-Schleife:

for values in originalDict.values(): 
    for ticksKey, ticksValue in ticks.items(): 
     if values[0] == ticksValue: 
      values[0] = ticksKey 

    #Change symbs and remove char combination 
    for symbsKey, symbsValue in symbs.items(): 
     comprComb = values[1] + "," + values[2] 

     if comprComb == symbsValue: 
      values[1] = str(symbsKey) 
      #del values[4] 
      #del values[4] 
      del values[2] 

ZUSÄTZLICHE INFORMATIONEN ZUSÄTZLICH: Der Grund, warum ich sie haben als Wörterbuch, weil die 500 000 Zeilen ist, Einige der Ticks treten mehr als einmal auf, also gebe ich ihnen einen int, der der Schlüssel im dict ist, also auch für das syms-Dictionary.

+0

Wenn die Schlüssel "0, 1, 2" sind, warum sind das keine Listen? –

+0

was meinst du? wie ich schon sagte, dies ist nur ein Beispiel für 4 Zeilen, die in diesem Fall haben 0,1,2 ... die Ticks und Symbs dict haben unterschiedliche Größe –

+0

Rewrite 'syms' und' Ticks', so dass die Werte die Schlüssel und Sie müssen nicht iterieren, sondern können nur die richtigen Werte nachschlagen? –

Antwort

1

Also zunächst alles, was Sie wollen Reverse die Abbildung, Sie sind zur Zeit von Wert suchen, was falsch ist und langsam:

ticks = {0: '6NH8', 1: '6AH8', 2: 'QMH8'} 
symbs = {0: 'F,A', 1: 'F,B'} 

ticks = {v: k for k, v in ticks.items()} Verwendung (gleich für symbs):

{'6NH8': 0, 'QMH8': 2, '6AH8': 1} # ticks 

{'F,A': 0, 'F,B': 1} # symbs 

Nun, da Sie gute Datenstrukturen haben, können Sie dies ziemlich schnell tun.

nun das Wörterbuch transformieren, die die Daten in eine Liste hält (nicht sicher, warum es ein Wörterbuch ist mit zu beginnen):

originalList = [originalDict[k] for k in range(len(originalDict))] 

Und erneut Kartenwerte:

for line in originalList: 
    line[0] = ticks[line[0]] 
    line[1:3] = [symbs["%s,%s" % tuple(line[1:3])]] 

Ergebnis:

[[0, 0, '0', '60541567', '60541567', '78.78', '20'], [0, 0, '0', '60541569', '60541569', '78.78', '25'], [1, 1, '0', '60541765', '60541765', '90.52', '1'], [2, 1, '0', '60437395', '60437395', '950.5', '1']] 
+0

danke reut :), Ill überprüfen Sie es und lassen Sie wissen :) –

+0

der Grund, warum ich die 0: tick1, 1: tick2 ist, weil ich fühle, dass es für eine Datei "kompakter" ist, oder denke ich falsch? –

+0

Wie unterscheidet es sich von einer Liste? Und eine Liste ist wahrscheinlich auch besser geeignet, um eine Datei darzustellen ('originalDict' ->' originalList'), da sie eine Reihenfolge hat. Ein Wörterbuch funktioniert nicht (zumindest nicht natürlich. Sie haben es unter Verwendung von Indizes als Orte durchgesetzt, ** was genau eine Liste ist **). In Wörterbüchern sollten die Schlüssel immer das sein, wonach Sie suchen. Nicht das, was du finden willst ... –

0

Sie können die Lookup beschleunigen, indem die Schlüssel und Werte in den ticks und symbs dicts invertiert und dann nur die richtigen Werte statt Iterieren sucht und vergleicht alle Werte in den dicts:

ticks_inv = {v: k for k, v in ticks.items()} 
symbs_inv = {v: k for k, v in symbs.items()} 

for values in originalDict.values(): 
    if values[0] in ticks_inv: 
     values[0] = ticks_inv[values[0]] 

    comprComb = "{v[1]},{v[2]}".format(v=values) 
    if comprComb in symbs_inv: 
     values[1] = symbs_inv[comprComb] 
     del values[2] 

Ergebnis ist das selbe wie mit Ihrem Code, sollte aber viel schneller sein, besonders wenn ticks und symbs groß sind. Dies setzt natürlich voraus, dass die Werte eindeutig sind, aber ansonsten würde Ihr Code nicht korrekt funktionieren.

+0

ok danke, lass mich versuchen zu ändern und zurück :) –

0

Ihr Wörterbuch ist rückwärts; Es verwendet nicht die Schlüssel-Lookup-Funktion des Wörterbuchs. Statt

for ticksKey, ticksValue in ticks.items(): 
    if values[0] == ticksValue: 
     values[0] = ticksKey 

versuchen

ticks = {'6NH8': 0, '6AH8': 1, 'QMH8': 2} 
... 
if values[0] in ticks: 
    values[0] = ticks[values[0]] 

Ein wenig seltsamen würde suchen sein nur

values[0] = ticks[values[0]] or values[0] 

Wenn Sie das tun, und in ähnlicher Weise mit symbs, Sie alle, aber den notwendigen outmost entfernen würden Schleife und sehen eine deutliche Leistungsverbesserung.

+0

danke, aber es ist durch 2 verschiedene Wörterbücher :) –

Verwandte Themen