43

Here is the dictionary I have

propertyList = {
    "id":           "int",
    "name":         "char(40)",

    "team":         "int",
    "realOwner":    "int",

    "x":            "int",
    "y":            "int",

    "description":  "char(255)",

    "port":         "bool",
    "secret":       "bool",
    "dead":         "bool",
    "nomadic":      "bool",

    "population":   "int",
    "slaves":       "int",
}

But when I print it out with "\n".join(myDict) I get this

name
nomadic
dead
port
realOwner
secret
slaves
team
y
x
population
id
description

I know that a dictionary is unordered but it comes out the same every time and I've no idea why.

Teifion
  • 108,121
  • 75
  • 161
  • 195
  • 38
    Unordered means order is none of your business. It does NOT mean the order is inconsistent. – S.Lott Feb 09 '09 at 00:11
  • 1
    @S. Lott: Precisely. That's what I've been taught on my CS course - 'the unordered collections will always have some order, *unordered* means that we should not rely on it' – Abgan Feb 09 '09 at 09:25
  • 5
    more precise: The ordering of python dictionaries is arbitary but deterministic (according to the python spec). Where deterministic means it will always behave the same way. – Philip Daubmeier Mar 23 '10 at 00:47
  • 2
    But if you are interested in order this is not the data structure that you should be looking for. Dictionary is an unordered collection of items. List and Tuples preserve order. –  Nov 12 '09 at 08:36
  • Now I've seen this question I suggest if you want to preserve the order you can put each dictionary key-value pair inside a tuple/list so they will be always with the same order –  Dec 28 '14 at 15:27
  • Algorithmic answer http://stackoverflow.com/questions/30537090/why-is-pythons-hash-function-treated-as-a-sort-function-on-some-sequence-of-num/30537091#30537091 – Mazdak May 29 '15 at 21:44

3 Answers3

80

For older versions of Python, the real question should be “why not?” — An unordered dictionary is usually implemented as a hash table where the order of elements is well-defined but not immediately obvious (the Python documentation used to state this). Your observations match the rules of a hash table perfectly: apparent arbitrary, but constant order.

Python has since changed its dict implementation to preserve the order of insertion, and this is guaranteed as of Python 3.7. The implementation therefore no longer constitutes a pure hash table (but a hash table is still used in its implementation).

Konrad Rudolph
  • 530,221
  • 131
  • 937
  • 1,214
  • 1
    It's well worth reading a comment from python's dictionary source file; I've already posted it in a stackoverflow post about "the best comment you've ever seen": http://is.gd/iSyN – llimllib Feb 09 '09 at 06:05
  • 1
    A bit of dict's internal implementation can be found here http://www.laurentluce.com/posts/python-dictionary-implementation/ . There was a nice presentation from one of python's coders, but can't find it at the moment (I think it was from PyCon Australia). – Maciej Gol Oct 02 '13 at 09:07
10

The specification for the built-in dictionary type disclaims any preservation of order, it is best to think of a dictionary as an unordered set of key: value pairs...

You may want to check the OrderedDict module, which is an implementation of an ordered dictionary with Key Insertion Order.

GarlicFries
  • 8,095
  • 5
  • 36
  • 53
Christian C. Salvadó
  • 807,428
  • 183
  • 922
  • 838
8

The only thing about dictionary ordering you can rely on is that the order will remain the same if there are no modifications to the dictionary; e.g., iterating over a dictionary twice without modifying it will result in the same sequence of keys. However, though the order of Python dictionaries is deterministic, it can be influenced by factors such as the order of insertions and removals, so equal dictionaries can end up with different orderings:

>>> {1: 0, 2: 0}, {2: 0, 1: 0}
({1: 0, 2: 0}, {1: 0, 2: 0})
>>> {1: 0, 9: 0}, {9: 0, 1: 0}
({1: 0, 9: 0}, {9: 0, 1: 0})
Miles
  • 31,360
  • 7
  • 64
  • 74