Wie indiziere ich in ein Wörterbuch?

92

Ich habe unten ein Wörterbuch:

colors = {
    "blue" : "5",
    "red" : "6",
    "yellow" : "8",
}

Wie indiziere ich den ersten Eintrag im Wörterbuch?

colors[0]wird KeyErroraus offensichtlichen Gründen ein zurückgeben.

Harpal
quelle
4
Was bedeutet "zuerst"? Wörterbücher haben keine Bestellung.
S.Lott
2
Wörterbücher ist jetzt Einfügung bestellt seit Python 3.7 Überprüfen Sie dies aus: stackoverflow.com/questions/39980323/…
Nikita Alkhovik
1
@ S.Lott Ich wette, er hätte nicht gefragt, ob er wüsste, dass sie ungeordnet sind :).
user7778287

Antworten:

109

Wörterbücher sind in Python-Versionen bis einschließlich Python 3.6 ungeordnet. Wenn Sie sich nicht um die Reihenfolge der Einträge kümmern und trotzdem über den Index auf die Schlüssel oder Werte zugreifen möchten, können Sie d.keys()[i]und d.values()[i]oder verwenden d.items()[i]. (Beachten Sie, dass diese Methoden eine Liste aller Schlüssel, Werte oder Elemente in Python 2.x erstellen. Wenn Sie sie also mehrmals benötigen, speichern Sie die Liste in einer Variablen, um die Leistung zu verbessern.)

Wenn Sie sich für die Reihenfolge der Einträge interessieren, können Sie ab Python 2.7 verwenden collections.OrderedDict. Oder verwenden Sie eine Liste von Paaren

l = [("blue", "5"), ("red", "6"), ("yellow", "8")]

Wenn Sie keinen Zugriff per Schlüssel benötigen. (Warum sind deine Zahlen übrigens Zeichenfolgen?)

In Python 3.7 sind normale Wörterbücher geordnet, sodass Sie sie nicht OrderedDictmehr verwenden müssen (aber Sie können es trotzdem - es ist im Grunde der gleiche Typ). Die CPython-Implementierung von Python 3.6 enthielt diese Änderung bereits. Da sie jedoch nicht Teil der Sprachspezifikation ist, können Sie sich in Python 3.6 nicht darauf verlassen.

Sven Marnach
quelle
2
Verwenden Sie in Python 2 d.iterkeys().next()anstelle von d.keys()[0], um einen der Schlüssel zu überprüfen, ohne ihn zu entfernen. Wenn das Wörterbuch sehr groß ist, wird es einen großen Unterschied in Bezug auf die Leistung machen. Gleiches gilt für Werte und Gegenstände. In Python 2.7 können Sie auch
diktierte
41
In Python 3 geben diese Aufrufe eine Ansicht anstelle einer tatsächlichen Liste zurück, sodass Sie sie in einen Aufruf von list () einschließen sollten. Andernfalls wird Folgendes angezeigt: "TypeError: Das Objekt 'dict_values' unterstützt keine Indizierung". Siehe diese SO-Frage: stackoverflow.com/questions/17431638/…
stifin
2
Nur eine kleine Korrektur: Sie können keine Elemente indizieren (), zumindest nicht in Python 3.
John Strong
1
Diese Antwort ist für Python 3.6+ veraltet, siehe Antwort von @Pasha unten.
Hans
1
@hans Diese Antwort ist für Python 3.7 veraltet, jedoch nicht für Python 3.6, da die auftragserhaltende Natur von Wörterbüchern ein Implementierungsdetail der CPython-Implementierung dieser Python-Version ist und kein offizieller Teil der Sprache. Ich werde diese Antwort entsprechend aktualisieren.
Sven Marnach
101

Wenn sich noch jemand mit dieser Frage befasst, ist die derzeit akzeptierte Antwort veraltet:

Seit Python 3.7 * behalten die Wörterbücher die Reihenfolge bei , das heißt, sie verhalten sich jetzt genau so, wie sie es collections.OrderedDictgewohnt sind. Leider gibt es immer noch keine dedizierte Methode zum Indizieren in keys()/ values()des Wörterbuchs, sodass das Abrufen des ersten Schlüssels / Werts im Wörterbuch wie folgt erfolgen kann

first_key = list(colors)[0]
first_val = list(colors.values())[0]

oder alternativ (dies vermeidet das Instanziieren der Schlüsselansicht in einer Liste):

def get_first_key(dictionary):
    for key in dictionary:
        return key
    raise IndexError

first_key = get_first_key(colors)
first_val = colors[first_key]

Wenn Sie einen n-ten Schlüssel benötigen , dann ähnlich

def get_nth_key(dictionary, n=0):
    if n < 0:
        n += len(dictionary)
    for i, key in enumerate(dictionary.keys()):
        if i == n:
            return key
    raise IndexError("dictionary index out of range") 

(* CPython 3.6 enthielt bereits geordnete Diktate, dies war jedoch nur ein Implementierungsdetail. Die Sprachspezifikation enthält geordnete Diktate ab 3.7.)

Pascha
quelle
Könnten Sie bitte den Link zur entsprechenden Dokumentation angeben?
Miind
3

Ein Element des Wörterbuchs anzusprechen ist wie auf einem Esel zu sitzen und die Fahrt zu genießen.

In der Regel ist Python DICTIONARY ordentlich

Wenn da ist

dic = {1: "a", 2: "aa", 3: "aaa"}

Nehmen wir nun an, wenn ich so gehe dic[10] = "b", wird es nicht immer so hinzugefügt

dic = {1:"a",2:"aa",3:"aaa",10:"b"}

Es kann sein wie

dic = {1: "a", 2: "aa", 3: "aaa", 10: "b"}

Oder

dic = {1: "a", 2: "aa", 10: "b", 3: "aaa"}

Oder

dic = {1: "a", 10: "b", 2: "aa", 3: "aaa"}

Oder eine solche Kombination.

So Faustregel ist DICTIONARY ist orderless !

Raj Damani
quelle
das ist sehr geradlinig ... ich mag es!
Alex Liu 33214
2

Wenn Sie ein geordnetes Wörterbuch benötigen, können Sie odict verwenden .

Utku Zihnioglu
quelle
odict unterstützt die Indizierung in keys (), values ​​() oder items () nicht.
Konstantin
2

Eigentlich habe ich eine neuartige Lösung gefunden, die mir wirklich geholfen hat. Wenn Sie sich besonders mit dem Index eines bestimmten Werts in einer Liste oder einem Datensatz befassen, können Sie einfach den Wert des Wörterbuchs auf diesen Index setzen!:

Schau nur:

list = ['a', 'b', 'c']
dictionary = {}
counter = 0
for i in list:
   dictionary[i] = counter
   counter += 1

print(dictionary) # dictionary = {'a':0, 'b':1, 'c':2}

Jetzt können Sie mithilfe von Hashmaps den Index Ihrer Einträge in konstanter Zeit abrufen (auch bekannt als viel schneller).

user3368835
quelle
1

Oh, das ist eine schwierige Frage. Was Sie hier haben, sind im Grunde zwei Werte für jeden Artikel. Dann versuchen Sie, sie mit einer Nummer als Schlüssel anzurufen. Leider ist einer Ihrer Werte bereits als Schlüssel festgelegt!

Versuche dies:

colors = {1: ["blue", "5"], 2: ["red", "6"], 3: ["yellow", "8"]}

Jetzt können Sie die Schlüssel nach Nummer anrufen, als wären sie wie eine Liste indiziert. Sie können die Farbe und Nummer auch anhand ihrer Position in der Liste referenzieren.

Beispielsweise,

colors[1][0]
// returns 'blue'

colors[3][1]
// returns '8'

Natürlich müssen Sie eine andere Methode finden, um zu verfolgen, an welcher Stelle sich jede Farbe befindet. Vielleicht können Sie ein anderes Wörterbuch haben, in dem der Schlüssel jeder Farbe als Wert gespeichert wird.

farben_schlüssel = {'blau': 1, 'rot': 6, 'gelb': 8}

Anschließend können Sie bei Bedarf auch die Farbtaste nachschlagen.

colours [colours_key ['blue']] [0] gibt 'blue' zurück

Sowas in der Art.

Und dann können Sie, während Sie gerade dabei sind, ein Diktat mit den Zahlenwerten als Schlüssel erstellen, sodass Sie sie immer verwenden können, um Ihre Farben nachzuschlagen, wissen Sie, wenn Sie sie brauchen.

Werte = {5: [1, 'blau'], 6: [2, 'rot'], 8: [3, 'gelb']}

Dann gibt (Farben [Farben_Taste [Werte [5] [1]] [0]) 'Blau' zurück.

Oder Sie könnten eine Liste von Listen verwenden.

Viel Glück!

Godfreyluck
quelle
0

Sie können nicht, da dictist ungeordnet. Sie können verwenden .popitem(), um ein beliebiges Element zu erhalten, aber das wird es aus dem Diktat entfernen.

Ignacio Vazquez-Abrams
quelle
next(iter(d.items()))( .iteritems()in Python 2) gibt Ihnen auch ein beliebiges Element (dasselbe in meinen Tests, was sinnvoll ist, da Popitem damit implementiert werden kann), entfernt das Element jedoch nicht.