people = ['mago','pipa','john','mat']
>>> for people in people:
print(people)
mago
pipa
john
mat
>>> for people in people:
print(people)
m
a
t
>>> for people in people:
print(people)
t
>>> for people in people:
print(people)
t
>>> for people in people:
print(people)
t
>>> for people in people:
print(people)
-
2change list name to `peoples` and then `for people in peoples: print(people` – Druta Ruslan May 18 '18 at 17:25
1 Answers
A for
loop does not create a new scope for the index; you are overwriting the list people
with the loop index people
.
A for
loop is almost syntactic sugar for the following code:
# for people in people: # iter() is called implicitly on the iterable
# print(people)
people_itr = iter(people)
while True:
try:
people = next(people_itr)
except StopIteration:
break
print(people)
del people_itr
So although you have a reference to the list originally referenced by people
, the name people
is constantly updated to reference one element of that list. When you run your second loop, people
is now a reference to the last string in the list. The third and subsequent loops represent a fixed point; an iterator over a string returns successive 1-character strings, so you quickly reach a point where the string is its own only element.
With your example, people
is bound to "mat"
, not your list, after the first loop. After the second (and third, and fourth) loop, people
is bound to "t"
.
You can see the same thing by chaining calls to __getitem__
(i.e., [-1]
):
>>> people[-1]
'mat'
>>> people[-1][-1]
't'
>>> people[-1][-1][-1]
't'
>>> people[-1][-1][-1][-1]
't'

- 497,756
- 71
- 530
- 681
-
1If it did, you would then need some way to refer to variables from the enclosing scope in the event you shadowed a name. – chepner May 18 '18 at 17:35
-
-
`nonlocal` wouldn't help here, unless you significantly changed its semantics. `nonlocal p` means that `p` here is the same object that `p` in the enclosing scope refers to; it doesn't let you access a shadowed name. – chepner May 18 '18 at 17:48
-
Oh I think I misunderstood you then -- why would you need to refer to a shadowed variable from an enclosing scope? You can't do that currently (since shadowing a variable simply redefines it) – Adam Smith May 18 '18 at 17:53
-
If a new scope did not allow access to shadowed names, then you may as well make sure to use unique names, but then there's no real need for a new scope. You seem to be saying that the loop index should simply not exist after the loop exits, but then you can't use a loop to search a container by exiting once the index is equal to the desired value. – chepner May 18 '18 at 18:00