Are there any applicable differences between dict.items()
and dict.iteritems()
?
From the Python docs:
dict.items()
: Return a copy of the dictionary’s list of (key, value) pairs.
dict.iteritems()
: Return an iterator over the dictionary’s (key, value) pairs.
If I run the code below, each seems to return a reference to the same object. Are there any subtle differences that I am missing?
#!/usr/bin/python
d={1:'one',2:'two',3:'three'}
print 'd.items():'
for k,v in d.items():
if d[k] is v: print '\tthey are the same object'
else: print '\tthey are different'
print 'd.iteritems():'
for k,v in d.iteritems():
if d[k] is v: print '\tthey are the same object'
else: print '\tthey are different'
Output:
d.items():
they are the same object
they are the same object
they are the same object
d.iteritems():
they are the same object
they are the same object
they are the same object
This question is related to
python
dictionary
python-2.x
dict.items()
returns a list of 2-tuples ([(key, value), (key, value), ...]
), whereas dict.iteritems()
is a generator that yields 2-tuples. The former takes more space and time initially, but accessing each element is fast, whereas the second takes less space and time initially, but a bit more time in generating each element.
If you have
dict = {key1:value1, key2:value2, key3:value3,...}
In Python 2, dict.items()
copies each tuples and returns the list of tuples in dictionary i.e. [(key1,value1), (key2,value2), ...]
.
Implications are that the whole dictionary is copied to new list containing tuples
dict = {i: i * 2 for i in xrange(10000000)}
# Slow and memory hungry.
for key, value in dict.items():
print(key,":",value)
dict.iteritems()
returns the dictionary item iterator. The value of the item returned is also the same i.e. (key1,value1), (key2,value2), ...
, but this is not a list. This is only dictionary item iterator object. That means less memory usage (50% less).
d.items() -> list(d.items())
d.iteritems() -> iter(d.items())
The tuples are the same. You compared tuples in each so you get same.
dict = {i: i * 2 for i in xrange(10000000)}
# More memory efficient.
for key, value in dict.iteritems():
print(key,":",value)
In Python 3, dict.items()
returns iterator object. dict.iteritems() is removed so there is no more issue.
dict.iteritems
is gone in Python3.x So use iter(dict.items())
to get the same output and memory alocation
You asked: 'Are there any applicable differences between dict.items() and dict.iteritems()'
This may help (for Python 2.x):
>>> d={1:'one',2:'two',3:'three'}
>>> type(d.items())
<type 'list'>
>>> type(d.iteritems())
<type 'dictionary-itemiterator'>
You can see that d.items()
returns a list of tuples of the key, value pairs and d.iteritems()
returns a dictionary-itemiterator.
As a list, d.items() is slice-able:
>>> l1=d.items()[0]
>>> l1
(1, 'one') # an unordered value!
But would not have an __iter__
method:
>>> next(d.items())
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: list object is not an iterator
As an iterator, d.iteritems() is not slice-able:
>>> i1=d.iteritems()[0]
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: 'dictionary-itemiterator' object is not subscriptable
But does have __iter__
:
>>> next(d.iteritems())
(1, 'one') # an unordered value!
So the items themselves are same -- the container delivering the items are different. One is a list, the other an iterator (depending on the Python version...)
So the applicable differences between dict.items() and dict.iteritems() are the same as the applicable differences between a list and an iterator.
The commands dict.items()
, dict.keys()
and dict.values()
return a copy of the dictionary's list of (k, v)
pair, keys and values.
This could take a lot of memory if the copied list is very large.
The commands dict.iteritems()
, dict.iterkeys()
and dict.itervalues()
return an iterator over the dictionary’s (k, v)
pair, keys and values.
The commands dict.viewitems()
, dict.viewkeys()
and dict.viewvalues()
return the view objects, which can reflect the dictionary's changes.
(I.e. if you del
an item or add a (k,v)
pair in the dictionary, the view object can automatically change at the same time.)
$ python2.7
>>> d = {'one':1, 'two':2}
>>> type(d.items())
<type 'list'>
>>> type(d.keys())
<type 'list'>
>>>
>>>
>>> type(d.iteritems())
<type 'dictionary-itemiterator'>
>>> type(d.iterkeys())
<type 'dictionary-keyiterator'>
>>>
>>>
>>> type(d.viewitems())
<type 'dict_items'>
>>> type(d.viewkeys())
<type 'dict_keys'>
In Py3.x, things are more clean, since there are only dict.items()
, dict.keys()
and dict.values()
available, which return the view objects just as dict.viewitems()
in Py2.x did.
Just as @lvc noted, view object isn't the same as iterator, so if you want to return an iterator in Py3.x, you could use iter(dictview)
:
$ python3.3
>>> d = {'one':'1', 'two':'2'}
>>> type(d.items())
<class 'dict_items'>
>>>
>>> type(d.keys())
<class 'dict_keys'>
>>>
>>>
>>> ii = iter(d.items())
>>> type(ii)
<class 'dict_itemiterator'>
>>>
>>> ik = iter(d.keys())
>>> type(ik)
<class 'dict_keyiterator'>
dict.iteritems()
: gives you an iterator. You may use the iterator in other patterns outside of the loop.
student = {"name": "Daniel", "student_id": 2222}
for key,value in student.items():
print(key,value)
('student_id', 2222)
('name', 'Daniel')
for key,value in student.iteritems():
print(key,value)
('student_id', 2222)
('name', 'Daniel')
studentIterator = student.iteritems()
print(studentIterator.next())
('student_id', 2222)
print(studentIterator.next())
('name', 'Daniel')
dict.iteritems() in python 2 is equivalent to dict.items() in python 3.
dict.items()
return list of tuples, and dict.iteritems()
return iterator object of tuple in dictionary as (key,value)
. The tuples are the same, but container is different.
dict.items()
basically copies all dictionary into list. Try using following code to compare the execution times of the dict.items()
and dict.iteritems()
. You will see the difference.
import timeit
d = {i:i*2 for i in xrange(10000000)}
start = timeit.default_timer() #more memory intensive
for key,value in d.items():
tmp = key + value #do something like print
t1 = timeit.default_timer() - start
start = timeit.default_timer()
for key,value in d.iteritems(): #less memory intensive
tmp = key + value
t2 = timeit.default_timer() - start
Output in my machine:
Time with d.items(): 9.04773592949
Time with d.iteritems(): 2.17707300186
This clearly shows that dictionary.iteritems()
is much more efficient.
If you want a way to iterate the item pairs of a dictionary that works with both Python 2 and 3, try something like this:
DICT_ITER_ITEMS = (lambda d: d.iteritems()) if hasattr(dict, 'iteritems') else (lambda d: iter(d.items()))
Use it like this:
for key, value in DICT_ITER_ITEMS(myDict):
# Do something with 'key' and/or 'value'.
Source: Stackoverflow.com