103

ジェネレーター関数の結果を python の enumerate() に渡すとどうなるか知りたいです。例:

def veryBigHello():
    i = 0
    while i < 10000000:
        i += 1
        yield "hello"

numbered = enumerate(veryBigHello())
for i, word in numbered:
    print i, word
    

列挙は怠惰に繰り返されますか、それともすべてを<enumerate object>最初に丸呑みしますか? 99.999% 確実に怠け者なので、ジェネレーター関数とまったく同じように扱うことができますか、それとも何か注意する必要がありますか?

4

4 に答える 4

115

怠け者です。それが事実であることを証明するのはかなり簡単です:

>>> def abc():
...     letters = ['a','b','c']
...     for letter in letters:
...         print letter
...         yield letter
...
>>> numbered = enumerate(abc())
>>> for i, word in numbered:
...     print i, word
...
a
0 a
b
1 b
c
2 c
于 2010-08-03T12:14:41.723 に答える
50

前の提案のいずれかよりもさらに簡単にわかります。

$ python
Python 2.5.5 (r255:77872, Mar 15 2010, 00:43:13)
[GCC 4.3.4 20090804 (release) 1] on cygwin
Type "help", "copyright", "credits" or "license" for more information.
>>> abc = (letter for letter in 'abc')
>>> abc
<generator object at 0x7ff29d8c>
>>> numbered = enumerate(abc)
>>> numbered
<enumerate object at 0x7ff29e2c>

enumerate が遅延評価を実行しなかった場合は、返さ[(0,'a'), (1,'b'), (2,'c')]れるか、または (ほぼ) 同等のものが返されます。

もちろん、enumerate は実際には単なる手の込んだジェネレーターです。

def myenumerate(iterable):
   count = 0
   for _ in iterable:
      yield (count, _)
      count += 1

for i, val in myenumerate((letter for letter in 'abc')):
    print i, val
于 2010-08-03T12:55:01.160 に答える
14

メモリ不足の例外を取得せずにこの関数を呼び出すことができるため、間違いなく怠惰です

def veryBigHello():
    i = 0
    while i < 1000000000000000000000000000:
        yield "hello"

numbered = enumerate(veryBigHello())
for i, word in numbered:
    print i, word
于 2010-08-03T12:15:23.263 に答える
0

他の誰か(sklearn)が書いたジェネレーターを使用していたので、ここでのアプローチでは機能しなかった古い学校の代替手段。

i=(-1)
for x in some_generator:
    i+=1
于 2020-10-15T01:41:51.103 に答える