Сортировка словаря в Python 3
Я работаю с Python 3.2.2 и уже более 3 часов ломаю голову над тем, как отсортировать словарь по его ключам. Мне удалось создать отсортированный список с двумя элементами, но я не могу превратить его обратно в отсортированный словарь.
Вот что у меня получилось:
myDic = {10: 'b', 3: 'a', 5: 'c'}
sorted_list = sorted(myDic.items(), key=lambda x: x[0])
Но, несмотря на все усилия, я не могу создать словарь из этого отсортированного списка. Как мне это сделать? Спасибо!
5 ответ(ов)
Вы можете отсортировать словарь по ключам в Python 3.7 следующим образом:
myDic = {10: 'b', 3: 'a', 5: 'c'}
sortDic = sorted(myDic.items())
print(dict(sortDic))
Вывод будет таким:
{3: 'a', 5: 'c', 10: 'b'}
Если вам нужна отсортированная lista кортежей, вы можете сделать следующее:
myDic = {10: 'b', 3: 'a', 5: 'c'}
sortDic = sorted(myDic.items())
print(sortDic)
Результат будет:
[(3, 'a'), (5, 'c'), (10, 'b')]
Таким образом, в первом случае вы получаете отсортированный словарь, а во втором — список кортежей, отсортированных по ключам.
dict
не сохраняет порядок элементов. Вам нужно использовать OrderedDict
: документация.
исправление
Пример использования:
>>> from collections import OrderedDict
>>> a = {'foo': 1, 'bar': 2}
>>> a
{'foo': 1, 'bar': 2}
>>> b = OrderedDict(sorted(a.items()))
>>> b
OrderedDict([('bar', 2), ('foo', 1)])
>>> b['foo']
1
>>> b['bar']
2
Обычные словари (dict
) в Python не могут быть настроены для предоставления ключей или элементов в определенном порядке. Для этого вы можете использовать тип OrderedDict
из модуля collections
. Обратите внимание, что OrderedDict
просто сохраняет порядок вставки. Если вы хотите, чтобы последующие просмотры/итераторы возвращали элементы в порядке, вам нужно сначала отсортировать записи перед инициализацией словаря. Например:
>>> myDic = {10: 'b', 3: 'a', 5: 'c'}
>>> sorted_list = sorted(myDic.items(), key=lambda x: x[0])
>>> myOrdDic = OrderedDict(sorted_list)
>>> myOrdDic.items()
[(3, 'a'), (5, 'c'), (10, 'b')]
>>> myOrdDic[7] = 'd'
>>> myOrdDic.items()
[(3, 'a'), (5, 'c'), (10, 'b'), (7, 'd')]
Если вы хотите поддерживать правильный порядок для вновь добавленных элементов, вам действительно потребуется использовать другую структуру данных, например, двоичное дерево или кучу. Этот подход с построением отсортированного списка и использованием его для инициализации нового экземпляра OrderedDict()
является неэффективным, если ваши данные не являются статичными.
Редактирование: Итак, если цель сортировки данных заключается лишь в том, чтобы распечатать их в порядке, подобном объекту dict
в Python, что-то вроде следующего должно подойти:
def pprint_dict(d):
strings = []
for k in sorted(d.keys()):
strings.append("%d: '%s'" % (k, d[k]))
return '{' + ', '.join(strings) + '}'
Обратите внимание, что эта функция не является гибкой в отношении типов пар ключ-значение (т. е. она ожидает, что ключи будут целыми числами, а соответствующие значения - строками). Если вам нужна большая гибкость, используйте вместо этого что-то вроде strings.append("%s: %s" % (repr(k), repr(d[k])))
.
Дикторы по определению неупорядочены. Основной причиной сортировки по ключам может быть необходимость получить данные в определённом порядке для удобства их дальнейшего использования или отображения. Например, если вы хотите отобразить словарь в виде списка, отсортированного по ключам, вы можете использовать метод sorted()
в сочетании с методом .items()
. Однако, как вы правильно отметили, при преобразовании обратно в словарь порядок ключей не сохраняется, так как словари не имеют фиксированного порядка элементов.
Ваш пример показывает, как можно отсортировать элементы словаря:
>>> myDic
{10: 'b', 3: 'a', 5: 'c'}
>>> sorted(myDic.items())
[(3, 'a'), (5, 'c'), (10, 'b')]
Тем не менее, при преобразовании отсортированного списка кортежей обратно в словарь итоговый словарь всё равно будет отображаться в произвольном порядке:
>>> print(dict(myDic.items()))
{10: 'b', 3: 'a', 5: 'c'}
Чтобы сохранить отсортированный порядок, вы можете использовать collections.OrderedDict
, который сохраняет порядок вставки элементов, или получать отсортированный список кортежей и использовать его для дальнейших операций, где порядок имеет значение.
Таким образом, если вам действительно нужно хранить порядок элементов, после сортировки лучше использовать маппинг вроде OrderedDict
или же работать со списками, чтобы избежать ситуации с произвольным порядком.
Ваш код выглядит неплохо, но есть несколько моментов, которые можно улучшить. Чтобы упорядочить словарь, вы можете использовать встроенную функцию sorted()
для получения отсортированных ключей, а затем создать новый словарь на основе этих ключей. Вот пример, который делает именно это:
def order_dic(dic):
return {key: dic[key] for key in sorted(dic.keys())}
В этом коде мы используем генератор словарей, что делает его более компактным и читабельным. Он возвращает новый словарь, где элементы упорядочены по ключам.
Если вы используете Python 3.7 или выше, стоит отметить, что словари сохраняют порядок вставки элемента, поэтому вы можете просто использовать dict(sorted(dic.items()))
, чтобы получить упорядоченный словарь:
def order_dic(dic):
return dict(sorted(dic.items()))
Этот метод также делает то же самое, но требует меньше строк кода и работает с элементами словаря напрямую.
Преобразование списка словарей в DataFrame pandas
Почему использовать dict.get(key) вместо dict[key]?
Как преобразовать вложенный словарь Python в объект?
Ошибка: "'dict' объект не имеет метода 'iteritems'"
Есть ли питоний способ объединить два словаря (сложив значения для ключей, которые присутствуют в обоих)?