To put it simply, the generator function feels like a
return can be created in the middle of the function.
However, the feature is that it does not end even if you do something like
Also, I will return them one by one, so I don't use much memory.
I will also explain the sub-generator added in python3.
Code created this time: https://github.com/KodairaTomonori/Qiita/tree/master/default_module/syntax
yield instead of
First of all, simply from the
fibonatti sequence generation functions that count numbers
def counter(): num = 0 while True: yield num num += 1 def fibonatti(): now = 0 next_num = 1 while True: yield now now, next_num = next_num, now + next_num if __name__ == '__main__': count = counter() print('print 0-3, for i in count') for i in count: print(i, end=', ') if i >= 3: print() break print('next_count, count.__next__()') print(count.__next__()) print('print 5-7, for i in count') for i in count: print(i, end=', ') if i >= 7: count.close() print() print('print fibonatti') for i in fibonatti(): if i > 100: break print(i, end=', ') print(i)
print 0-3, for i in count 0, 1, 2, 3, next_count, count.__next__() 4 print 5-7, for i in count 5, 6, 7, print fibonatti 0, 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 144
counter function is simple, starting at
num = 0 and entering an infinite loop of
yield num for each loop.
counter called? Sometimes
num + 1 and then
yield num is returned.
Each time it is called, a
+ 1 value is returned.
When using it, it is written in the place of
main, but if you put it in the
for statement, it will return the value
0,1,2,3 in sequence for each loop.
You can save its state (
num) by defining it as a variable with
count = counter ().
count.__next__ () will return the next number, that is,
The following for statement also adds one by one and returns it as before.
However, unlike before, the state of
count stops at
num = 4, so this loop starts at
So, at the end, when it became
7 or more, I did
count.close ()to end the loop.
If you use
.close (), you can exit the
for statement and lose the function as a generator of
After this, spit out
count.__next__ () and
fibonatti is almost the same, so there is no particular problem.
In this case, the generator is placed directly with
fibonatti (), so after exiting the
for statement, the generator where
now, next_num is stored will go somewhere.
The fact that it can be turned with a
for statement can be made into a
list by enclosing it in
list (), but in that case, if you do not set a limit in the generator function, you will die in an infinite loop, so be careful.
You can pass arguments each time with
.send (x) gives
x to the position of
yield, so you have to execute
.__ next__ ()once.
def generator(step): val = 0 prev = 0 while True: if step == None: step = prev prev = step val += step step = yield val if __name__ == '__main__': gen = generator(0) print(gen.__next__(), end=', ') for i in [1,2,3,4,5,6]: print(gen.send(i) , end=', ') print()
0, 1, 3, 6, 10, 15, 21,
generator function is a program that adds the received argument
First, set the
generator (0) initial value to 0.
.__next__ () to go to
step = yield val.
0 will be returned.
Then enter the for statement and turn from
1 to 6.
gen.send (i) is executed, ʻi
is entered at the previous step = yield val
. In other words, if you do gen.send (i)
, you get step = i
. I will loop like that. Here, if you do .__ next __ ()
without using.send ()
, you will get step = None`.
The sub-generator will execute the generator if you do
yield from generator.
generator is a generator function.
This makes recursion very convenient.
A sample program for generating permutations containing the same is explained.
def ex_permutation(iterable, now_list=): if not iterable: yield now_list return for i in [iterable.index(i) for i in set(iterable) ]: yield from permutation(iterable[:i] + iterable[i+1:], now_list + [iterable[i] ]) if __name__ == '__main__': permu = ex_permutation([2,2,3]) for i in permu: print(i)
[2, 2, 3] [2, 3, 2] [3, 2, 2]
I don't care what's inside, but I'm just doing it recursively using
set () so that it doesn't get covered.
So you can write recursively with
Finally, it returns
now_list when the contents of ʻiterable` are empty.
I don't know what it is, but it's convenient!
It seems to be confusing without this.
You can return a value in the middle of the function with
You can end the generator function with
Do the following with
You can pass a value with
yield from is convenient.