파이썬리스트 반복자 동작 및 다음 (반복자)


147

치다:

>>> lst = iter([1,2,3])
>>> next(lst)
1
>>> next(lst)
2

따라서 예상대로 반복기의 진행은 동일한 객체를 변경하여 처리됩니다.

이것은 사실입니다.

a = iter(list(range(10)))
for i in a:
   print(i)
   next(a)

두 번째 요소마다 건너 뛰기 : next반복자를 한 번 진행시켜야 하는 호출 , 루프에 의한 암시 적 호출은 두 번째로 진행해야 하며이 두 번째 호출의 결과는에 할당됩니다 i.

그렇지 않습니다. 루프 는 목록의 모든 항목을 건너 뛰지 않고 인쇄 합니다.

내 첫 번째 생각은 루프 iter가 전달 된 것을 호출하기 때문에 이것이 일어날 수 있고 이것이 독립적 인 반복자를 줄 수 있다는 것 iter(a) is a입니다. 이것은 그렇지 않습니다 .

그렇다면 왜이 next경우 반복자를 진행시키는 것처럼 보이지 않습니까?

답변:


197

당신이 보는 것은 인터프리터 가 각 반복을 인쇄 next()하는 i것 외에도 반환 값을 에코 하는 것입니다.

>>> a = iter(list(range(10)))
>>> for i in a:
...    print(i)
...    next(a)
... 
0
1
2
3
4
5
6
7
8
9

또한 인터프리터 인터프리터 등에서 0출력되는 의 반환 값 print(i), 의 출력값도 마찬가지 입니다. 반복은 5 회 뿐이며, 각 반복마다 2 개의 라인이 터미널에 기록됩니다.1next()

next()사물 의 출력을 할당하면 예상대로 작동합니다.

>>> a = iter(list(range(10)))
>>> for i in a:
...    print(i)
...    _ = next(a)
... 
0
2
4
6
8

또는 대화식 인터프리터 에코 와 출력 을 구별하기 위해 추가 정보를 인쇄 하십시오 print().

>>> a = iter(list(range(10)))
>>> for i in a:
...    print('Printing: {}'.format(i))
...    next(a)
... 
Printing: 0
1
Printing: 2
3
Printing: 4
5
Printing: 6
7
Printing: 8
9

다시 말해, next()예상대로 작동하지만 대화식 인터프리터에 의해 에코되는 반복자에서 다음 값을 리턴하기 때문에 루프에 자체 반복자 사본이 있다고 생각하게됩니다.


13
나는 통역사의 이러한 행동을 알지 못했다. 나는 많은 시간을 잃기 전에 실제 문제를 해결하면서 그것에 대해 궁금해한다는 것을 알게되어 기쁩니다.
brandizzi

5
... * dies *. 최악의 경우, 일주일 전에 누군가에게이 해석기 동작을 정확하게 언급 한 것을 기억할 수 있습니다.
lvc

흥미 롭군 나는 다음을 시도했다 : next (a); print i 그리고 나는 1로 뛰어 가서 1,3,5,7,9를 인쇄 할 것이라고 생각했다. 그러나 여전히 0,2,4,6,8입니다. 왜?
user2290820

3
i이미 할당. next(a)는 다음 반복 2이에 할당 된 i다음 a다시 이동 하고 인쇄하는 i등을 의미합니다.
Martijn Pieters

1
n이 홀수 인 경우에는 작동하지 않습니다 . 목록이 exausted 된 후 호출 StopIteration될 때 excepetio nis가 발생 next(a)합니다.
Raf

13

무슨 일이 일어나고 있는지는 next(a)a의 다음 값 을 반환하는데, 이는 영향을받지 않기 때문에 콘솔에 출력됩니다.

당신이 할 수있는 일은이 값을 가진 변수에 영향을 미칩니다.

>>> a = iter(list(range(10)))
>>> for i in a:
...    print(i)
...    b=next(a)
...
0
2
4
6
8

8

기존 답변이 코드 예제에서 본질적으로 신비로운 것을 간접적으로 나타 내기 때문에 약간 혼란스러워 합니다. * "print i"및 "next (a)"모두 결과가 인쇄됩니다.

원래 시퀀스의 대체 요소를 인쇄하고 있으며 "next (a)"문이 인쇄되는 것은 예상치 못한 일이므로 "print i"문이 모든 값을 인쇄하는 것처럼 나타납니다.

그 점에서 변수에 "next (a)"의 결과를 할당하면 그 결과의 인쇄가 금지되어 "i"루프 변수의 대체 값만 인쇄된다는 것이 더 명확 해집니다. 이와 유사하게 "print"문을 작성하면 더 명확하게 명확하게 표현됩니다.

(기존 답변 중 하나는 블록으로 평가 된 예제 코드가 있으므로 인터프리터가 "next (a)"에 대한 중간 값을보고하지 않기 때문에 다른 답변을 반박합니다.)

일반적으로 질문에 대한 대답은 당신이 대답을 알고 나면 분명한 것에 대해 명백합니다. 어려울 수 있습니다. 당신이 그들을 이해하면 마찬가지로 비판 답변. 흥미 롭군...


2

Python / 컴퓨터에 문제가 있습니다.

a = iter(list(range(10)))
for i in a:
   print(i)
   next(a)

>>> 
0
2
4
6
8

예상대로 작동합니다.

Python 2.7 및 Python 3+에서 테스트되었습니다. 둘 다에서 제대로 작동


5
@lvc와 동일한 결과를 얻습니다 (그러나 스크립트로 실행될 때 IDLE에서만 가능))
jamylak

3
@Inbar Rose 스크립트로 실행하는 경우에만 해당됩니다.
Quintec

1
대화식 쉘을 통해 코드를 넣는 동작입니다. 함수가 사용되지 않고 값을 반환하면 인터프리터는이를 디버그 출력으로 쉘에 인쇄합니다.
Reishin

2

여전히 이해하지 못하는 사람들을 위해.

>>> a = iter(list(range(10)))
>>> for i in a:
...    print(i)
...    next(a)
... 
0 # print(i) printed this
1 # next(a) printed this
2 # print(i) printed this
3 # next(a) printed this
4 # print(i) printed this
5 # next(a) printed this
6 # print(i) printed this
7 # next(a) printed this
8 # print(i) printed this
9 # next(a) printed this

다른 사람들이 이미 말했듯이 next예상대로 반복기를 1 씩 증가시킵니다. 반환 값을 변수에 할당해도 동작이 마술처럼 바뀌지 않습니다.


1

함수로 호출되면 원하는 방식으로 작동합니다.

>>> def test():
...     a = iter(list(range(10)))
...     for i in a:
...         print(i)
...         next(a)
... 
>>> test()
0
2
4
6
8
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.