-1

I wanted to clarify some points about dictionaries in Python, which may help some other Python enthusiasts in the future.

Let's start with a simple dictionary.

foo = {'a_2': 4, 'b_2': 5, 'a_1': 2, 'b_1': 1}

and displaying foo gives,

In [31]: foo
Out[31]: {'a_1': 2, 'a_2': 4, 'b_1': 1, 'b_2': 5}

As one can see, foo seems to be 'unordered'. However, upon reading further I've found that dictionaries are not inherently ordered, and the output when a dictionary is displayed is just based on the hash values of the keys.

My confusion arises when I loop over the dictionary using foo.iteritems() or foo.items() (both give the same result.)

for k, v in foo.iteritems():
    print '{}: {}'.format(k, foo[k])

b_1: 1
b_2: 5
a_2: 4
a_1: 2

This output ordering does not agree with the order I entered the keys/values in foo or the way they are outputted when foo is called.

Does this have to do with how foo.iteritems() generates its keys/values or something else?

I am using Python 2.7 on Ubuntu

Jordan Pagni
  • 454
  • 3
  • 11
  • your repl is probably just sorting it for you to make it easier to read. additionally, foo is not "called". your repl is just displaying foo. there's no way to "call" a dictionary – acushner Apr 07 '17 at 22:16
  • IPython is sorting the keys when you display `foo`. – user2357112 Apr 07 '17 at 23:51

2 Answers2

1

According to PEP 372, In current Python versions, the widely used built-in dict type does not specify an order for the key/value pairs stored. This makes it hard to use dictionaries as data storage for some specific use cases.

Dict in Python haven't any order :) for this usage, you can use collections.OrderedDict like this:

foo = {'a_2': 4, 'b_2': 5, 'a_1': 2, 'b_1': 1}
import collections
order = collections.OrderedDict(foo)

for k,v in order.items():
    print k,v

You can read about the OrderedDict

RaminNietzsche
  • 2,683
  • 1
  • 20
  • 34
  • So I would assume this inconsistency I see is not only based on the inherent lack of ordering, but also possibly the REPL built in? – Jordan Pagni Apr 07 '17 at 22:29
1

Right. The orders may or may not agree. The ordering is not guaranteed. The implementation is free to choose whatever order is convenient. In other words, what you see above may not be the same order you get from Python, then Cython, then a LISP-based Python, etc.

In fact, with my current installations, even Python 2.7 and Python 3.5 differ.

If you need the order, use the OrderedDict object. If you're merely curious about the implementation, I suggest that you find documentation for your particular implementation.

Prune
  • 76,765
  • 14
  • 60
  • 81
  • For extra fun, orders can differ between different runs of the same Python version due to hash randomization. – kindall Apr 07 '17 at 22:30
  • Ok thanks guys. This makes more sense now. I think there are a few factors affecting my output including dicts not being ordered, my REPL as pointed out by acushner in his reply, and also my version of Python. However I think it all stems from the fact that dictionaries are not inherently ordered. I will probably use ordered dictionaries or sort the ones i have – Jordan Pagni Apr 07 '17 at 22:31