19

Please see below code snippet for join method (used Python 2.7.2):

iDict={'1_key':'abcd','2_key':'ABCD','3_key':'bcde','4_key':'BCDE'}
'--'.join(iDict)

Result shown as

'2_key--1_key--4_key--3_key'

Please comment why only keys are joined? Also the sequence is not in order.

Note - below are the individual methods.

  • '--'.join(iDict.values()) ==> 'ABCD--abcd--BCDE--bcde' ==> the sequence is not in order
  • '--'.join(iDict.keys()) ==> '2_key--1_key--4_key--3_key' ==> the sequence is not in orde
TechnoBee
  • 311
  • 1
  • 2
  • 6
  • 4
    Please get rid of the trailing semicolons at the end of each line of code. This is Python! – Matthias Jun 02 '14 at 14:49
  • `only keys are joined` that's what it does. use `items()` if you need the values as well. `the sequence is not in order` that's what it does, dict keys are not sorted. Use an `OrderedDict`. By `that's what it does`, I mean that this is the information you get when you bother to read the doc. – njzk2 Jun 02 '14 at 15:06
  • 1
    This question appears to be off-topic because the question is `why does it behave as documented rather than how I would like it to?` – njzk2 Jun 02 '14 at 15:07

3 Answers3

23

If you see the docs, you learn that iterating over dict returns keys.

You need to iterate over dict.items(), that it over tuples (key, value):

'--'.join(iDict.items())

If you need to have key AND value joined in one string, you need to explicitly tell Python how to do this:

'--'.join('{} : {}'.format(key, value) for key, value in iDict.items())
m.wasowski
  • 6,329
  • 1
  • 23
  • 30
6

Python dictionaries are unordered (or rather, their order is arbitrary), and when you iterate on them, only the keys are returned:

>>> d = {'0':0, '1':1, '2':2, '3':3, '4':4}
>>> print(d)
{'4': 4, '1': 1, '0': 0, '3': 3, '2': 2}

If you need both keys and values, use iDict.items().

If you need ordering, use collections.OrderedDict.

Henry Keiter
  • 16,863
  • 7
  • 51
  • 80
  • As of 3.8 (and even a little earlier), differences between ordinary dict and ordered dict are small. – PatrickT Jun 16 '20 at 07:21
5

Iteration over a dictionary only ever yields keys:

>>> list(iDict)
['2_key', '1_key', '4_key', '3_key']

See the dict() documentation:

iter(d)
Return an iterator over the keys of the dictionary. This is a shortcut for iterkeys().

Both list() and str.join() will call iter() on their arguments to iterate over the elements.

Dictionaries are unordered containers; their order stems from the underlying data structure and depends on the insertion and deletion history of the keys.

This is documented under dict.items():

CPython implementation detail: Keys and values are listed in an arbitrary order which is non-random, varies across Python implementations, and depends on the dictionary’s history of insertions and deletions.

Also see Why is the order in dictionaries and sets arbitrary?

Community
  • 1
  • 1
Martijn Pieters
  • 1,048,767
  • 296
  • 4,058
  • 3,343