Difference between iterable and iterator in Python

Hello everyone, in this tutorial, we are going the see the difference between iterable and iterator in Python. Let’s start with an example. Say, we have a Python list as shown below.

li = [1, 3, 5, 7, 9]

The above list is an iterable. We can iterate through its element using __next__() after creating the iterator object from it. This can be done using iter() built-in function. Once we have created an iterator from an iterable we can access its elements one by one using the built-in method next(). See below.

li = [1, 3, 5, 7, 9]
li_iterator = iter(li)

print(next(li_iterator))
print(next(li_iterator))
print(next(li_iterator))
print(next(li_iterator))
print(next(li_iterator))

Output:

1
3
5
7
9

The next() method will raise StopIterationn exception when there are no more elements remaining to iterate over. See the given code and its output.

li = [1, 3, 5, 7, 9]
li_iterator = iter(li)

print(next(li_iterator))
print(next(li_iterator))
print(next(li_iterator))
print(next(li_iterator))
print(next(li_iterator))
print(next(li_iterator))

Output:

1
3
5
7
9
Traceback (most recent call last):
  File "/home/901bb7fa22a03980479ac921070d8965.py", line 9, in <module>
    print(next(li_iterator))
StopIteration

We can also use loops to iterate through an iterable or an iterator.

Also, note that every iterator is an iterable but the vice versa is not true. That means we cannot use an iterable with the next() method to access its next elements. For example, a set is not an iterator. It is iterable and requires a call to the iter() method to create an iterator object.

Note: An object is iterable if the class it belongs to has __iter__() method defined and an iterable is an iterator if the class it belongs to has __next__() method defined.

Role of __iter__() and __next__() functions

As we have seen we can use iter() function to create an iterator from an iterable. Now in order to make this work, we need to make sure that the class of the object has either __iter__() method which can return an iterator or __getitem__() whose indexing starts with zero. Hence an iterator is returned. Iterators use __next__() method to iterate through its elements. Have a look at the below code.

class NaturalNumbers:
    
    def __init__(self, n):
        self.n = n
        self.cur = 1
        
    def __iter__(self):
        return self
        
    def __next__(self):
        if self.cur == self.n+1:
            raise StopIteration
        else:
            ret = self.cur
            self.cur += 1 
            return ret
            
nums = NaturalNumbers(5)
for n in nums:
    print (n)

Output:

1
2
3
4
5

I hope this post was helpful.

Thank you.

Also read: Iterators in Python

Leave a Reply