Your last bullet point is most likely the cause. At python3.3, hash randomization was enabled by default to address a security concern. Basically, the idea is that you now never know exactly how your strings will hash (which determines their order in the dictionary).
Here's a demo:
d = {"a": 1, "b": 2, "c": 3}
print(d)
On my machine, with python3.4, this results in 3 differently ordered results:
$ python3.4 test.py
{'a': 1, 'c': 3, 'b': 2}
$ python3.4 test.py
{'c': 3, 'b': 2, 'a': 1}
$ python3.4 test.py
{'b': 2, 'c': 3, 'a': 1}
Before hash randomization, if you knew how a string would hash, a malicious attacker with enough knowledge of your application could feed it data to cause dictionary lookup to run in O(n) time instead of the usual O(1) for dictionary lookups. That could cause serious performance degradation for some applications.
You can disable the hash randomization as documented here. At some point, they also introduced a -R
flag to python which enabled hash randomization on an "opt in" basis. This option is at least available for python3.2, so you could use that to test our hypothesis.