I am very new in Python and I am finding some difficulties trying to understand how exactly works this generator implementation example calcolating Fibonacci squence:
class Fib:
def __init__(self, nn):
print("__init__")
self.__n = nn
self.__i = 0
self.__p1 = self.__p2 = 1
def __iter__(self):
print("__iter__")
return self
def __next__(self):
print("__next__")
self.__i += 1
if self.__i > self.__n:
raise StopIteration
if self.__i in [1, 2]:
return 1
ret = self.__p1 + self.__p2
self.__p1, self.__p2 = self.__p2, ret
return ret
for i in Fib(10):
print(i)
So I have this Fib class. As usual it contains the __init__() constructor method that take the number of wich I wand to calculate the Fibonacci seqience and set to 0 the i property (because 0 is the first Fibonacci number of each sequence) and set 1 the second and the third number of the sequence (so it starts from 0,1,1).
Then I have the __iter__() method that return itself (so is it returnin a Fib object, is it correct?).
Finnally there is the __next__() method that should return the next item of the seuqence. When the last element is reached it raise a StopIteration exception. Otherwise it calculate the next fibonacci number and return it.
Outside the generator class I am using this for loop:
for i in Fib(10):
print(i)
to calculate the first 10 Fibonacci number.
And here I have some doubts:
1) When I do Fib(10) I am calling the constructor (the __init__() method), so I am calling it one time. Is it correct?
2) The __next__() method is called when I have to obtain the next Fibonacci number. Ok...But who is calling this method? I suppose that it is automatically called by the FOR loop but I am not visualizing how it happens.
3) The FOR loop it seems to me that it is calling the constructor (__init__() method passing to it the number of which it have to calculate the Fibonacci sequence. But what is the sens of the __iter__() method. Who is calling it?