-1

I have the following testcase_dict.py script:

print([{x: 'hello', 'x': 'y'} for x in [1, 2]])

I run this script, and every 15 times, 2-4 times it gives me distincted results:

 $ for i in $(seq 15); do python testcase_dict.py; done
[{1: 'hello', 'x': 'y'}, {2: 'hello', 'x': 'y'}]
[{1: 'hello', 'x': 'y'}, {2: 'hello', 'x': 'y'}]
[{1: 'hello', 'x': 'y'}, {'x': 'y', 2: 'hello'}]
[{1: 'hello', 'x': 'y'}, {2: 'hello', 'x': 'y'}]
[{1: 'hello', 'x': 'y'}, {2: 'hello', 'x': 'y'}]
[{1: 'hello', 'x': 'y'}, {2: 'hello', 'x': 'y'}]
[{'x': 'y', 1: 'hello'}, {'x': 'y', 2: 'hello'}]
[{1: 'hello', 'x': 'y'}, {2: 'hello', 'x': 'y'}]
[{1: 'hello', 'x': 'y'}, {'x': 'y', 2: 'hello'}]
[{1: 'hello', 'x': 'y'}, {2: 'hello', 'x': 'y'}]
[{1: 'hello', 'x': 'y'}, {2: 'hello', 'x': 'y'}]
[{1: 'hello', 'x': 'y'}, {'x': 'y', 2: 'hello'}]
[{'x': 'y', 1: 'hello'}, {'x': 'y', 2: 'hello'}]
[{1: 'hello', 'x': 'y'}, {2: 'hello', 'x': 'y'}]
[{1: 'hello', 'x': 'y'}, {2: 'hello', 'x': 'y'}]

Why this happens and how can I prevent it. This may be a reason of some raise conditions which are strongly unwelcome.

My Python version is 3.5.2.

My question DOES NOT regard specific order, just deterministic one.

pt12lol
  • 2,332
  • 1
  • 22
  • 48
  • I realize dictionaries are not ordered and I do not need `OrderedDict`. I would like to have only deterministic order. There is nothing random here. – pt12lol Jun 29 '17 at 12:32
  • Then use a list of tuples? – cs95 Jun 29 '17 at 12:33
  • @pt12lol you might be interested in the information in the answers for this question: https://stackoverflow.com/questions/9010222/how-can-python-dict-have-multiple-keys-with-same-hash – Will Da Silva Jun 29 '17 at 12:34
  • @pt12lol> dicts are not ordered. This means the have NO ORDER. Therefore they cannot have a deterministic order. If you want to **display** them in a specific order, you must order the keys by yourself. – spectras Jun 29 '17 at 12:46
  • @spectras ok, but still iteration through keys is not deterministic. – pt12lol Jun 29 '17 at 12:49
  • @pt12lol> indeed it's not. It's not advertised as such either. Iterate on `sorted(mydict.keys())` if you want it to be consistent. The only guarantee is that iterating a dictionnary will yield entries in the same order if you do it several times without modifying it. This applies only to a single dictionnary object, not across dictionnaries, even if they have the same content. – spectras Jun 29 '17 at 12:51

2 Answers2

2

dict is not ordered, and can display arbitrary ordering.... you should read about collections.OrderedDict: https://docs.python.org/3/library/collections.html

Ofer Sadan
  • 11,391
  • 5
  • 38
  • 62
  • `dict`s are ordered from 3.6 on (unofficially in some versions of 3.5, I think) –  Jun 29 '17 at 12:34
  • @hop which is not to be relied on, as stressed many times by core devs since it is an implementation detail and not a language feature. The only thing that *can* be relied on in 3.6 in this regard is the presevredorder of class attributes and functions kwargs. – DeepSpace Jun 29 '17 at 12:37
  • 1
    @a_guest: sounds like you are confusing "sorted" and "ordered". in principle one and the same `dict` (used to be) is free to return keys in an ordered whenever you call `.keys()` or similar. that they don't is just an implementation detail. also, since recreating the "same key-value pairs" might not be possible, the distinction is moot. –  Jun 29 '17 at 12:40
  • @DeepSpace: which you can read in my answer. "dict is not ordered" is simply a false statement. –  Jun 29 '17 at 12:41
0

Although dictionaries are deterministically ordered in Python from version 3.6 on (but not before), you should not rely on that fact.

If you need a dictionary like type that guarantees order, use collections.OrderedDict or sort the keys before iterating over them.

"Ordered" in both cases means: remembers the order entries were added.

  • I realize dictionaries are not ordered and I do not need OrderedDict. I would like to have only deterministic order. There is nothing random in my script. – pt12lol Jun 29 '17 at 12:34
  • @pt12lol: there, fixed it for you. –  Jun 29 '17 at 12:42
  • why the downvote? –  Jun 29 '17 at 12:42
  • Because it is not an answer to my question at all. – pt12lol Jun 29 '17 at 12:43
  • @pt12lol> your question is meaningless. Something that is unordered, that is which has no order cannot have a deterministic order. – spectras Jun 29 '17 at 12:45
  • @spectras: thanks! I was not sure I was in the correct movie there for a minute. –  Jun 29 '17 at 12:46
  • @spectras nope, I would suppose it can be ordered based on hashes and I am completely surprised it changes through specific calls history. – pt12lol Jun 29 '17 at 12:48