Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]


Groups > comp.lang.python > #60711 > unrolled thread

Re: For-each behavior while modifying a collection

Started byWolfgang Maier <wolfgang.maier@biologie.uni-freiburg.de>
First post2013-11-28 17:21 +0000
Last post2013-11-28 17:21 +0000
Articles 1 — 1 participant

Back to article view | Back to comp.lang.python

This discussion starts older than the indexed window; earlier articles aren't shown. The article labeled Started by below is the oldest one visible, not the original post.


Contents

  Re: For-each behavior while modifying a collection Wolfgang Maier <wolfgang.maier@biologie.uni-freiburg.de> - 2013-11-28 17:21 +0000

#60711 — Re: For-each behavior while modifying a collection

FromWolfgang Maier <wolfgang.maier@biologie.uni-freiburg.de>
Date2013-11-28 17:21 +0000
SubjectRe: For-each behavior while modifying a collection
Message-ID<mailman.3365.1385659341.18130.python-list@python.org>
Valentin Zahnd <v.zahnd <at> gmail.com> writes:

> 
> Hello
> 
> For-each does not iterate ober all entries of collection, if one
> removes elements during the iteration.
> 
> Example code:
> 
> def keepByValue(self, key=None, value=[]):
>     for row in self.flows:
>         if not row[key] in value:
>             self.flows.remove(row)
> 
> It is clear why it behaves on that way. Every time one removes an
> element, the length of the colleciton decreases by one while the
> counter of the for each statement is not.
> The questions are:
> 1. Why does the interprete not uses a copy of the collection to
> iterate over it? Are there performance reasons?
> 2. Why is the counter for the iteration not modified?
> 
> Valentin
> 

I guess because it's difficult to generalize this idea.
Python for loops use the iterator protocol, i.e., in order to be usable in a
for loop all an object has to provide is an __iter__ and a __next__ method,
but your suggestion #1 would require it to define a copy method in addition.
As for #2: there is no such thing as a loop counter in a standard for loop,
but it's the iterated object that decides on the next value the loop will
see, and there's no way to move back, e.g.:
class jumplist (list):
    def __iter__(self):
        n=0
        while True:
            if n%3:
                yield self[n]
            else:
                yield None
            n+=1
            if n>=len(self):
                break

jumper=jumplist(range(10))

for element in jumper:
    print(element)

---->
None
1
2
None
4
5
None
7
8
None

Best,
Wolfgang

[toc] | [standalone]


Back to top | Article view | comp.lang.python


csiph-web