Has Next in Python Iterators

Stefan Behnel stefan_ml at behnel.de
Mon Oct 25 07:02:27 EDT 2010


Kelson Zawack, 25.10.2010 12:33:
> The example I have in mind is list like [2,2,2,2,2,2,1,3,3,3,3] where
> you want to loop until you see not a 2 and then you want to loop until
> you see not a 3.  In this situation you cannot use a for loop as
> follows:
>
> foo_list_iter = iter([2,2,2,2,2,2,1,3,3,3,3])
> for foo_item in foo_list_iter:
>      if foo_item != 2:
>          break
> because it will eat the 1 and not allow the second loop to find it.
> takeWhile and dropWhile have the same problem.  It is possible to use
> a while loop as follows:
>
> foo_list_item = foo_list_iter.next()
> while foo_list_item == 2:
>      foo_list_item = foo_list_iter.next()
> while foo_list_item == 3:
>      foo_list_item = foo_list_iter.next()

Why not combine the two into this:

     foo_list_iter = iter([2,2,2,2,2,2,1,3,3,3,3])
     for item in foo_list_iter:
         if item != 2:
            print item
            break
     # not sure what to do with the "1" here, hope you do ...
     for item in foo_list_iter:
         if item != 3:
            print item

Also take a look at the itertools module, which provide little helpers like 
takewhile(), groupby() and some other nice filters.


> As for the feasibly of implementing a has_next function I agree that
> you cannot write one method that will provide the proper functionality
> in all cases, and thus that you cannot create a has_next for
> generators.  Iterators however are a different beast, they are
> returned by the thing they are iterating over and thus any special
> cases can be covered by writing a specific implementation for the
> iterable in question.

Well, then just write the specific iterable wrappers that you need for your 
specific case. If you do it well, you can make your code a lot easier to 
read that way. And that's usually a very good proof that something like 
"has_next()" is not needed at all and just complicates things.


> This sort of functionality is possible to
> implement, because java does it.

Like that was an argument for anything. Java iterators also require you to 
implement "remove()". I can't remember ever doing anything else but 
throwing an exception in my implementation for that. Bad design isn't a 
good reason for a feature to be copied.

Stefan




More information about the Python-list mailing list