2016-08-04 33 views
-2

Wenn ich so etwas tun:Hinzufügen von verschachtelten Wörterbücher in Python von Ausbeute

x1={'Count': 11, 'Name': 'Andrew'} 
x2={'Count': 14, 'Name': 'Matt'} 
x3={'Count': 17, 'Name': 'Devin'} 
x4={'Count': 20, 'Name': 'Andrew'} 
x1 

vars=[x1,x2,x3,x4] 
for i in vars: 
    my_dict[i[group_by_column]]=i 
my_dict 

Dann erhalte ich:

defaultdict(int, 
      {'Andrew': {'Count': 20, 'Name': 'Andrew'}, 
      'Devin': {'Count': 17, 'Name': 'Devin'}, 
      'Geoff': {'Count': 10, 'Name': 'Geoff'}, 
      'Matt': {'Count': 14, 'Name': 'Matt'}}) 

das ist genau das, was ich will.

Wenn ich jedoch versuche, dies von einem Objekt zu replizieren, in dem ein yield eingebaut ist, überschreibt es sehr viel Wert im Wörterbuch. Zum Beispiel cast_record_stream ist eine Funktion, so dass die folgenden Wörterbücher wie gewünscht ergibt:

{'Count': 11, 'Name': 'Andrew'} 
{'Count': 14, 'Name': 'Matt'} 
{'Count': 17, 'Name': 'Devin'} 
{'Count': 20, 'Name': 'Andrew'} 
{'Count': 5, 'Name': 'Geoff'} 
{'Count': 10, 'Name': 'Geoff'} 

Also dann, wenn ich ausführen, um diese Funktion es kommt aus falsch:

for line in cast_record_stream: 
    record_name=line['Name'] 
    my_dict[record_name]=line 

    defaultdict(<type 'int'>, {'Devin': {'Count': 10, 'Name': 'Geoff'}, 
'Matt': {'Count': 10, 'Name': 'Geoff'}, 
'Geoff': {'Count': 10, 'Name': 'Geoff'}, 
'Andrew': {'Count': 10, 'Name': 'Geoff'}}) 

Bin ich hier ein Problem, dass ich die Schaffung kann nicht sehen? Ich dachte, es würde nur einen Wert nach dem anderen hinzufügen.

+1

Es könnte hilfreich sein, Ihren Code mit dem gewünschten yield zu zeigen. –

+0

Es sind mehrere Funktionen miteinander verkettet, so dass es nur verwirrend werden würde. Der wichtige Teil ist, dass es jedes der oben aufgelisteten Wörterbücher hervorbringt, von denen einige einen wiederholten 'Namen' haben. – vashts85

+0

Meine Vermutung:' cast_record_stream' modifiziert und liefert das gleiche Wörterbuch wieder. Stellen Sie sicher, dass Sie vor der Abgabe ein neues Diktat erstellen. –

Antwort

-1

Ein paar Probleme. Erstens ist cast_record_stream eine Funktion, nehme ich an, so dass Ihre erste Zeile sollte

for line in cast_record_stream(): 

Wörterbücher können keine doppelten Schlüssel haben sein. Wenn Ihr Iterator zwei Geoffs zurückgibt, überschreibt dieser immer den ersten. Wenn Sie doppelte Namen erwarten, sollten Sie eine andere Methode zum Speichern Ihrer Daten als ein Wörterbuch in Betracht ziehen.

R

+0

Es ist ein Funktionsergebnis, das alle einzelnen Wörterbücher enthält, aber diese werden einzeln nacheinander ausgegeben. – vashts85

+0

Beachten Sie, wie der Schlüssel in "Devin": {'Count': 10, 'Name': "Geoff"} ist anders als der Name im Diktat. Die Diktate kommen mit den richtigen (eindeutigen) Namen aus dem Generator, aber sie werden alle vor dem Drucken geändert. Ich vermute, dass alle auf dieselbe Instanz verweisen. –

0

Ich kann Ihr Problem nicht reproduzieren. Hier ist eine vollständige Reproduktion, außer dass es perfekt funktioniert. Dies zeigt, dass die Ideen, die Sie in Ihrem OP beschrieben haben, korrekt sind und Sie einen anderen Fehler im echten Code haben.

cast_list = [ 
    {'Count': 11, 'Name': 'Andrew'}, 
    {'Count': 14, 'Name': 'Matt'}, 
    {'Count': 17, 'Name': 'Devin'}, 
    {'Count': 20, 'Name': 'Andrew'}, 
    {'Count': 5, 'Name': 'Geoff'}, 
    {'Count': 10, 'Name': 'Geoff'}, 
] 

def cast_record_stream(): 
    for record in cast_list: 
     yield record 

from collections import defaultdict 
d = {} 
for record in cast_record_stream(): 
    print record 
    d[record['Name']] = record 
print d 

Per der Diskussion in den Kommentaren unten, ich glaube, Sie record_name = line [ ‚Name‘] manchmal speichern, aber es manchmal bekommen nicht aktualisiert, weil Sie etwas iterieren, die Sie nicht sollten, was möglicherweise zu in einer for-Schleife, die niemals die Zeile ausführt, die record_name aktualisieren würde.

+0

Also ich versuche das und es funktioniert nicht ....."cast_record_stream" wird nicht als Funktion erkannt, da es sich in meinem Code um ein Objekt handelt, das die yield von der vorherigen Funktion – vashts85

+0

speichert, obwohl Sie sagten, es sei eine Generatorfunktion. Wenn das der eine Ertrag ist, dann kann man nicht darüber iterieren. Sie addieren nur diese eine Ausbeute, und Sie sind jetzt fertig. Es gibt eine Iteration woanders (sonst wäre es dumm, einen Generator zu haben), und hier können Sie das vollständige Diktat erstellen. –

+0

Ich bin mir nicht sicher, ob ich folge, sorry. Ich bin neu bei Python und alles, was ich sagen kann, ist, dass 'cast_recode_stream' keine Funktion ist, sondern die' yield' Ergebnisse einer vorherigen Funktion speichert. Ich möchte nicht alles posten, weil es etwas trainiert, und ich mache mir Sorgen um Datenschutzprobleme. – vashts85