[python] ¿Cómo puedo ordenar un diccionario por clave?



Answers

Los diccionarios mismos no tienen elementos ordenados como tales, si desea imprimirlos, etc., en algún orden, estos son algunos ejemplos:

En Python 2.4 y superior:

mydict = {'carl':40,
          'alan':2,
          'bob':1,
          'danny':3}

for key in sorted(mydict):
    print "%s: %s" % (key, mydict[key])

da:

alan: 2
bob: 1
carl: 40
danny: 3

(Python debajo de 2.4 :)

keylist = mydict.keys()
keylist.sort()
for key in keylist:
    print "%s: %s" % (key, mydict[key])

Fuente: http://www.saltycrane.com/blog/2007/09/how-to-sort-python-dictionary-by-keys/

Question

¿Cuál sería una buena forma de pasar de {2:3, 1:89, 4:5, 3:0} a {1:89, 2:3, 3:0, 4:5} ?
Revisé algunas publicaciones, pero todas usan el operador "ordenado" que devuelve tuplas.




from operator import itemgetter
# if you would like to play with multiple dictionaries then here you go:
# Three dictionaries that are composed of first name and last name.
user = [
    {'fname': 'Mo', 'lname': 'Mahjoub'},
    {'fname': 'Abdo', 'lname': 'Al-hebashi'},
    {'fname': 'Ali', 'lname': 'Muhammad'}
]
#  This loop will sort by the first and the last names.
# notice that in a dictionary order doesn't matter. So it could put the first name first or the last name first. 
for k in sorted (user, key=itemgetter ('fname', 'lname')):
    print (k)

# This one will sort by the first name only.
for x in sorted (user, key=itemgetter ('fname')):
    print (x)



Los dictados de Python no están ordenados. Por lo general, esto no es un problema ya que el caso de uso más común es hacer una búsqueda.

La forma más sencilla de hacer lo que quiera es crear una collections.OrderedDict insertando los elementos en orden ordenado.

ordered_dict = collections.OrderedDict([(k, d[k]) for k in sorted(d.keys())])

Si necesita iterar, como otros sugirieron, la forma más sencilla sería repetir las claves ordenadas. Ejemplos-

Valores de impresión ordenados por claves:

# create the dict
d = {k1:v1, k2:v2,...}
# iterate by keys in sorted order
for k in sorted(d.keys()):
    value = d[k]
    # do something with k, value like print
    print k, value

Obtener una lista de valores ordenados por claves:

values = [d[k] for k in sorted(d.keys())]



Hay una serie de módulos de Python que proporcionan implementaciones de diccionario que mantienen automáticamente las claves en orden ordenado. Considere el módulo sortedcontainers , que es pura implementación de Python y fast-as-C. También hay una comparación de rendimiento con otras opciones populares comparadas entre sí.

El uso de un dict ordenado es una solución inadecuada si necesita agregar y eliminar constantemente pares clave / valor al mismo tiempo que itera.

>>> from sortedcontainers import SortedDict
>>> d = {2:3, 1:89, 4:5, 3:0}
>>> s = SortedDict(d)
>>> s.items()
[(1, 89), (2, 3), (3, 0), (4, 5)]

El tipo SortedDict también admite búsquedas y eliminación de ubicaciones indexadas que no es posible con el tipo de dict incorporado.

>>> s.iloc[-1]
4
>>> del s.iloc[2]
>>> s.keys()
SortedSet([1, 2, 4])



Encontrado de otra manera:

import json
print json.dumps(d, sort_keys = True)

upd:
1. Esto también ordena objetos anidados (gracias @DanielF).
2. Los diccionarios de Python están desordenados, por lo tanto, este es sutable para imprimir o asignar a str.




Aquí encontré la solución más simple para ordenar el dict de python por clave usando pprint . p.ej.

>>> x = {'a': 10, 'cd': 20, 'b': 30, 'az': 99} 
>>> print x
{'a': 10, 'b': 30, 'az': 99, 'cd': 20}

pero al usar pprint devolverá el dict ordenado

>>> import pprint 
>>> pprint.pprint(x)
{'a': 10, 'az': 99, 'b': 30, 'cd': 20}



Creo que lo más fácil es ordenar la dicción por clave y guardar la clave ordenada: par de valores en una nueva dicción.

dict1 = {'renault': 3, 'ford':4, 'volvo': 1, 'toyota': 2} 
dict2 = {}                  # create an empty dict to store the sorted values
for key in sorted(dict1.keys()):
    if not key in dict2:    # Depending on the goal, this line may not be neccessary
        dict2[key] = dict1[key]

Para hacerlo más claro:

dict1 = {'renault': 3, 'ford':4, 'volvo': 1, 'toyota': 2} 
dict2 = {}                  # create an empty dict to store the sorted     values
for key in sorted(dict1.keys()):
    if not key in dict2:    # Depending on the goal, this line may not be  neccessary
        value = dict1[key]
        dict2[key] = value



dictionary = {1:[2],2:[],5:[4,5],4:[5],3:[1]}

temp=sorted(dictionary)
sorted_dict = dict([(k,dictionary[k]) for i,k in enumerate(temp)])

sorted_dict:
         {1: [2], 2: [], 3: [1], 4: [5], 5: [4, 5]}



Chicos, están complicando las cosas ... es realmente simple

from pprint import pprint
Dict={'B':1,'A':2,'C':3}
pprint(Dict)

El resultado es:

{'A':2,'B':1,'C':3}



Si tienes un dict, por ejemplo:

not_ordered_dict = {5 : "5555", 9 : "9999", 1 : "1111"}

ordered_dict = {}

for key in sorted(not_ordered_dict):
    ordered_dict[key] = not_ordered_dict[key]   



Como otros han mencionado, los diccionarios son inherentemente desordenados. Sin embargo, si el problema se limita a mostrar diccionarios de forma ordenada, puede anular el método __str__ en una subclase de diccionario y usar esta clase de diccionario en lugar de la sentencia incorporada. P.ej.

class SortedDisplayDict(dict):
   def __str__(self):
       return "{" + ", ".join("%r: %r" % (key, self[key]) for key in sorted(self)) + "}"


>>> d = SortedDisplayDict({2:3, 1:89, 4:5, 3:0})
>>> d
{1: 89, 2: 3, 3: 0, 4: 5}

Tenga en cuenta que esto no cambia nada acerca de cómo se almacenan las claves, el orden en que volverán cuando itere sobre ellas, etc., cómo se muestran con print o en la consola de python.




Links