2015-11-02 61 views
1

我想创建一个具有类似生成器的方法的类。我对发电机相当陌生。这里是我的代码:类中的python生成器

class MyGen: 

    def __init__(self): 
     self.a = 0 

    def create_generator(self): 
     yield self.a 
     self.a += 1 

if __name__ == "__main__": 
    myGenInstance = MyGen() 
    myGen = myGenInstance.create_generator() 
    for i in range(3): 
     print(next(myGen)) 

我得到这个错误:

Traceback (most recent call last): 
0 
File "C:/Users/tvavr/PycharmProjects/filter/geneŕator_test.py", line 17, in <module> 
print(next(myGen)) 
StopIteration 
Process finished with exit code 1 

我缺少什么?

+4

您的生成器只返回一个值(它只是一个不在任何循环内的yield语句)。试图正确地获得另一个值会导致“StopIteration”异常,表示没有更多的值可以产生。 –

+0

这是非常值得的时间来阅读:http://stackoverflow.com/a/231855/1832539 – idjaw

+0

换句话说:你不会错过任何东西,它的行为完全如预期。 – jonrsharpe

回答

0

读取代码时,没有错误,python引发的异常是正常行为。

create_generator方法只能产生一个值,因为只使用了一个产量。

认为:

class Mygen: 
    def __init__(self): 
     self.a = 0 

    def create_generator(self): 
     yield self.a 
     self.a += 1 

     yield self.a 
     self.a += 1 

     yield self.a 

当你运行如下注意到发生了什么代码:

if __name__ == "__main__": 
my_gen_instance = MyGen() 
my_gen = my_gen_instance.create_generator() 
for i in range(3): 
    print('the value number', i, 'is:', next(myGen)) 

输出将是:

the value number 0 is 0 
the value number 1 is 1 
the value number 2 is 2 

现在,如果我们改变范围从3到4,看看会发生什么:

if __name__ == "__main__": 
    my_gen_instance = MyGen() 
    my_gen = my_gen_instance.create_generator() 
    for i in range(4): 
     print('the value number', i, 'is:', next(myGen)) 

输出将是:

the value number 0 is 0 
the value number 1 is 1 
the value number 2 is 2 
Traceback (most recent call last): 
    File "pygen.py", line 21, in <module> 
    print('the value number', i, 'is', next(my_gen)) 
StopIteration 

因为发电机是特殊类型的迭代器,他们抛出一个StopIteration时,他们都用尽像正常的迭代器

因此,为了避免这种情况你必须预见到这种行为其中,因为你需要尽可能多的收益,最好的方式是如下创建MyGen类中无限发生器:

class MyGen: 
    def __init__(self): 
     self.a = 0 

    def create_generator(self): 
     while True: 
      yield self.a 
      self.a += 1 

现在,您可以根据需要对通过此方法创建的生成器进行迭代。