8

I want to sort dictionary keys in a "natural order". If I have a dictionary with the keys

    d = {"key1" : object, "key11" : object, "key2" : object, "key22" : object", "jay1" : object, "jay2" : object}

I want to sort this dictionary so the result is:

    d = { "jay1" : object, "jay2" : object, "key_1" : object, "key_2" : object, "key_11" : object, "key_22" : object"}
user2909250
  • 261
  • 5
  • 10
  • 1
    Use https://docs.python.org/2/library/collections.html#collections.OrderedDict – marcadian Jun 12 '14 at 03:42
  • 2
    Dictionaries are not ordered. You can't control the order of dictionary keys. – BrenBarn Jun 12 '14 at 03:42
  • Are you asking how to "sort the dictionary" (in which case the question is a duplicate) or how to sort (anything) by natural order (pretty sure it's a duplicate anyway)? – Bakuriu Jun 12 '14 at 13:21
  • 2
    I don't believe this is a duplicate, because the question it is marked a duplicate of is about standard sorting, while this question is about natural sorting. – ThomasW Nov 27 '17 at 06:58
  • Should be reopened as it is about sorting by natural order, which is what I found this question for when googling. – Cornelius Roemer Feb 07 '23 at 18:37

4 Answers4

5

You can change your dict into OrderedDict:

import collections, re

d = {"key1" : 'object', "key11" : 'object', "key2" : 'object', "key22" : 'object', "jay1" : 'object', "jay2" : 'object'}


my_fun = lambda k,v: [k, int(v)]

d2 = collections.OrderedDict(sorted(d.items(), key=lambda t: my_fun(*re.match(r'([a-zA-Z]+)(\d+)',t[0]).groups())))

print(d2)
#reslt: OrderedDict([('jay1', 'object'), ('jay2', 'object'), ('key1', 'object'), ('key11', 'object'), ('key2', 'object'), ('key22', 'object')])

Basically, what is happening here, that I split the strings into 'string' part and number part. Number part is changed to int, and the sorting happens using these two values.

Marcin
  • 215,873
  • 14
  • 235
  • 294
2

As others have said, dictionaries are not ordered. However, if you want to iterate through these keys in a natural order, you could do something like the following:

d = {"key1" : object, "key11" : object, "key2" : object, "key22" : object, "jay1" : object, "jay2" : object}
sortedKeys = sorted(d.keys())
print sortedKeys
for key in sortedKeys:
    print d[key]
Bryan
  • 1,938
  • 13
  • 12
1

You can't order dictionaries because their order is seemingly arbitrary (it's actually not). Instead, you can sort the items() using natsort.natsorted():

d = {"key1" : object, "key11" : object, "key2" : object, "key22" : object, "jay1" : object, "jay2" : object}
print natsort.natsorted(d.items()) #[('jay1', <type 'object'>), ('jay2', <type 'object'>), ('key1', <type 'object'>), ('key2', <type 'object'>), ('key11', <type 'object'>), ('key22', <type 'object'>)]
A.J. Uppal
  • 19,117
  • 6
  • 45
  • 76
0

In Python, {'a': object, 'b': object} is exactly the same as {'b': object, 'a': object} because dictionaries are not ordered.

T.C.
  • 133,968
  • 17
  • 288
  • 421
DanielSank
  • 3,303
  • 3
  • 24
  • 42