如何按键的数字顺序对字典进行排序 Python

28 投票
4 回答
69217 浏览
提问于 2025-04-17 21:23

这里是字典的样子:

{'57481': 50, '57480': 89, '57483': 110, '57482': 18, '57485': 82, '57484': 40}  

我想把这个字典按数字顺序排序,结果应该是:

{'57480': 89, '57481': 50, '57482': 18, '57483': 110, '57484': 40, '57485': 82} 

我试过用 sorted(self.docs_info.items),但是没有成功。

4 个回答

4

在Python 3中,sorted()这个函数有一个可选的参数叫key。而在3.6及以上版本中,dict会保持插入的顺序。

key是一个函数,它接收一个参数,用来从可迭代对象中的每个元素提取出一个用于比较的关键字(比如,key=str.lower)。默认值是None,这意味着直接比较元素。

所以,想要的效果可以这样实现。

>>> d = {'57481': 50, '57480': 89, '57483': 110, '57482': 18, '57485': 82, '57484': 40}
>>> for key, value in sorted(d.items(), key=lambda item: int(item[0])):
...     print(key, value)
57480 89
57481 50
57482 18
57483 110
57484 40
57485 82

或者如果想要创建一个新的排序字典。

>>> d = {'57481': 50, '57480': 89, '57483': 110, '57482': 18, '57485': 82, '57484': 40}
>>> d_sorted = {key:value for key, value in sorted(d.items(), key=lambda item: int(item[0]))}
>>> d_sorted
{'57480': 89, '57481': 50, '57482': 18, '57483': 110, '57484': 40, '57485': 82}

d.items()会返回一个包含元组的列表,比如('57480': 89)等等。这个lambda函数会处理这个元组,并对第一个值应用int函数。然后,结果会用来进行比较。

5

如果你发现反复对元素进行排序和插入到有序字典里太慢了,可以考虑使用PyPI上的一些排序字典实现。SortedDict这种数据类型可以有效地保持它的键是有序的。sortedcontainers模块就包含了这样一种实现。

从PyPI安装非常简单:

pip install sortedcontainers

如果你不能使用pip install,那么可以直接从这个开源库下载sortedlist.py和sorteddict.py文件。SortedContainers是用纯Python实现的,但速度和C语言实现一样快。

安装完成后,只需:

In [1]: from sortedcontainers import SortedDict

In [6]: SortedDict({'57481': 50, '57480': 89, '57483': 110, '57482': 18, '57485': 82, '57484': 40})
Out[6]: SortedDict({'57480': 89, '57481': 50, '57482': 18, '57483': 110, '57484': 40, '57485': 82})

sortedcontainers模块还维护了一个性能比较,可以对比几种流行的实现。

10

标准的Python字典是“无序”的,也就是说里面的元素没有固定的顺序。如果你想要一个有顺序的字典,可以使用OrderedDict。你可以查看一下这个文档来了解更多信息。

from collections import OrderedDict

d = {'57481': 50, '57480': 89, '57483': 110, '57482': 18, '57485': 82, '57484': 40}
OrderedDict(sorted(d.items(), key=lambda t: t[0]))
# OrderedDict([('57480', 89), ('57481', 50), ('57482', 18), ('57483', 110), ('57484', 40), ('57485', 82)])
27

如果你只需要按键来排序,那你已经完成了95%的工作。假设你的字典叫做 docs_info

for key, value in sorted(docs_info.items()): # Note the () after items!
    print(key, value)

因为字典的键总是唯一的,所以对 docs_info.items()(这是一系列元组)调用 sorted 就相当于只按键来排序。

需要注意的是,包含数字的字符串排序可能会让人感到意外!比如 "11" 会被认为是比 "2" 小的。如果你需要按数字排序,我建议把键改成 int 类型,而不是 str 类型;例如:

int_docs_info = {int(k) : v for k, v in docss_info.items()}

这样做当然只是改变了你访问字典元素的顺序,这通常就足够了(因为如果你不访问它,排序又有什么关系呢?)。如果出于某种原因你需要字典本身是“排序过的”,那么你需要使用 collections.OrderedDict,它会记住 插入项目的顺序。所以你可以先像上面那样对字典进行排序,然后从排序后的(键,值)对创建一个 OrderedDict

sorted_docs_info = collections.OrderedDict(sorted(docs_info.items()))

撰写回答