Wie initialisiere ich ein Diktat mit Schlüsseln aus einer Liste und einem leeren Wert in Python?

251

Ich möchte davon profitieren:

keys = [1,2,3]

dazu:

{1: None, 2: None, 3: None}

Gibt es eine pythonische Methode?

Dies ist ein hässlicher Weg, dies zu tun:

>>> keys = [1,2,3]
>>> dict([(1,2)])
{1: 2}
>>> dict(zip(keys, [None]*len(keys)))
{1: None, 2: None, 3: None}
Juanjo Conti
quelle

Antworten:

389

dict.fromkeys([1, 2, 3, 4])

Dies ist eigentlich eine Klassenmethode, daher funktioniert sie auch für Diktat-Unterklassen (wie collections.defaultdict). Das optionale zweite Argument gibt den Wert an, der für die Schlüssel verwendet werden soll (standardmäßig:) None.

Thomas Wouters
quelle
153
Seien Sie vorsichtig beim Initialisieren auf etwas Veränderliches: Wenn Sie z. B. aufrufen, dict.fromkeys([1, 2, 3], [])werden alle Schlüssel derselben Liste zugeordnet, und wenn Sie einen ändern, werden alle geändert.
Charleslparker
8
Das Initialisieren mit {k:[] for k in [1, 2, 3]}ist jedoch immer noch sicher.
Aziz Alto
263

Niemand wollte eine Lösung zum Verständnis von Diktaten geben?

>>> keys = [1,2,3,5,6,7]
>>> {key: None for key in keys}
{1: None, 2: None, 3: None, 5: None, 6: None, 7: None}
Adrien Plisson
quelle
32
Ich glaube, es wurde auf 2.7
wim
21
Dies ist nett und leidet nicht unter dem Referenzproblem, das die akzeptierte Antwort hat.
Charleslparker
Auf diese Weise können Sie auch einen Standardwert zuweisen (z False. B. ).
Neverendingqs
Dies ist der sauberste und pythonischste Weg in Python3 IMO
Bede Constantinides
4
Durch die Verwendung eines dict-comp kann der Wert auch das Ergebnis des Aufrufs einer Funktion sein (die auf Wunsch den Schlüssel als Argument übergeben werden kann) - dies ist also ein sehr leistungsfähiger Mechanismus.
Martineau
56
dict.fromkeys(keys, None)
Dominic Cooney
quelle
2
genial, ich wollte leere Listen,dict.fromkeys(keys, [])
Myon
12
@muon Das ist mit ziemlicher Sicherheit nicht das, was du willst, siehe charleslparker Kommentar .
Gerrit
Funktioniert in Python Version 2.6.6.
Mike Finch
2
Achtung: Dadurch wird das Diktat mit allen Schlüsselpunkten auf denselben Einzelwert initialisiert
Mendi Barel
16
>>> keyDict = {"a","b","c","d"}

>>> dict([(key, []) for key in keyDict])

Ausgabe:

{'a': [], 'c': [], 'b': [], 'd': []}
Mayur Koshti
quelle
1
Während dieser Code die Frage möglicherweise beantwortet, würde die Bereitstellung eines zusätzlichen Kontexts darüber, wie und / oder warum das Problem gelöst wird, den langfristigen Wert der Antwort verbessern.
Francesco Menzani
4
Der Name keyDictist irreführend, da die erste Codezeile a setund nicht a zurückgibt dict.
Bryan Oakley
10
d = {}
for i in keys:
    d[i] = None
inspectorG4dget
quelle
1
Warum wirft Python einen Fehler aus wie : TypeError: 'type' object is not iterable?
FaCoffee
1
@FrancescoCastellani Weil listist ein Typ. Wenn Sie nicht so etwas haben list = [], gibt Ihnen die obige Methode immer den gleichen Fehler
smac89
1

In vielen Workflows , bei denen Sie einen Standard / Anfangswert für beliebige Tasten anhängen möchten, müssen Sie nicht brauchen , um Hash jede Taste einzeln vor der Zeit. Sie können verwenden collections.defaultdict. Beispielsweise:

from collections import defaultdict

d = defaultdict(lambda: None)

print(d[1])  # None
print(d[2])  # None
print(d[3])  # None

Dies ist effizienter und erspart das Hashing aller Schlüssel bei der Instanziierung. Darüber hinaus defaultdicthandelt es sich um eine Unterklasse von dict, sodass normalerweise keine Rückkonvertierung in ein reguläres Wörterbuch erforderlich ist.

Für Workflows, in denen Sie Steuerelemente für zulässige Schlüssel benötigen , können Sie dict.fromkeysgemäß der akzeptierten Antwort Folgendes verwenden:

d = dict.fromkeys([1, 2, 3, 4])
jpp
quelle