python knowledge -- iterators and generators

Posted by bhogg on Sat, 22 Jan 2022 19:23:00 +0100

Pre knowledge

Iteration: iteration is the activity of repeating the feedback process, and its purpose is usually to approach the desired goal or result. Each repetition of a process (function) is called an "iteration", and the result of each iteration (function return) will be used as the initial value of the next iteration (parameters passed into the function).
For example, Fibonacci series:
0 1 1 2 3 5 8 13 23.........

F(0)=0,F(1)=1, F(n)=F(n - 1)+F(n - 2)(n ≥ 2,n ∈ N)

iterator

  1. Iterator: is a class with__ iter__ () and__ next__ () class of method,
  2. Iterator object: is an instantiated object of the iterator class

remarks:

  • Iterator objects can be traversed using regular for statements
  • String, list, or tuple objects can be used to create iterators.
  • iter(): the built-in function of the class, which returns an iterator object (there are _iter _ () methods and__ next__ () method), then self is also an iterator object)
  • next(): the built-in function of the class, which returns the next data

Instance 1 custom iterator class

class MyNumbers:     # Because the MyNumbers class contains__ iter__ () and__ next__ () function, so MyNumbers is an iterator
  def __iter__(self):  # Returns an iterator object
    self.a = 1
    return self
 
  def __next__(self):   # Return to next data
    if self.a <= 5:
      x = self.a
      self.a += 1
      return x
    else:
      raise StopIteration  # Exceptions are used to identify the completion of iterations and prevent infinite loops__ next__ In the () method, we can set the StopIteration exception to be triggered after completing the specified number of cycles to end the iteration.
 
myclass = MyNumbers()   # myclass is an iterator object
 
for x in myclass:   # Iterator objects can use a for loop
  print(x)
  
  
  
>>>
1
2
3
4
5

Instance 2 strings, lists, tuples, and dictionaries can all be used to create iterators.

typestr: 'abc'list: [1,2,3]int: 1,2,3Iterator: iter([1,2,3])Generator: def g(): yeild 1dict: {'a':1, 'b':2, 'c':3}
IteratableTrueTrueFalseTrueTrue{'a':1, 'b':2, 'c':3}
IteratorFalseFalseFalseTrueTrueFlase
# Strings, lists, tuples, dictionaries can be used to create iterators

# my = 'this_is_a_string'  # string
# my = [1, 2, 3, 4, 5]  # listd
# my = ('a', 'b', 'c', 'd', 'e')  # tuple
my = {'a': 1, 'b': 2, 'c': 3, 'd': 4, 'e': 5}  # dictionary
it = iter(my)  # Create iterator object
print(next(it))  # The next element of the output iterator
print(next(it))
print(next(it))
print(next(it))
print(next(it))


>>>
a
b
c
d
e

generator

  1. The function of yield appears (Python interpreter will treat it as a generator class)
  2. Generator object: an object instantiated using the "generator function". Internally, the object is created according to the "generator class generator". The generator also declares the iter and _ next methods. The generator meets the definition of the iterator. The generator is a kind of iterator

example

#!/usr/bin/python3  
import sys  
def fibonacci(n): # Generator function - Fibonacci   
	a, b, counter = 0, 1, 0    
	while True:        
		if (counter > n):            
 			return        
		yield a        
		a, b = b, a + b        
		counter += 1 
		
f = fibonacci(10) # f is an iterator that is returned by the generator  

while True:    
	try:        
		print (next(f), end=" ")    
	except StopIteration:        
		sys.exit()

Iteratable object

  1. Iteratable class: Yes__ iter__ () class of method
  2. Iteratable object: an object created by an iteratable class; an iteratable object can perform a for loop; iterator objects and generator objects are special cases of iteratable objects
  3. dir(): see what methods the object has
    If v1 = range()
    dir(v1) can output the methods owned by v1

Judgment of iteratable objects and iterators

  1. Check whether the object contains the following methods through dir():
  • Iteratable objects: Containing__ iter__ () method
  • Iterators: including__ iter__ () and__ next__ () method
  1. Judging by Iterable and Iterator
typestr: 'abc'list: [1,2,3]int: 1,2,3Iterator: iter([1,2,3])Generator: def g(): yeild 1dict: {'a':1, 'b':2, 'c':3}
IteratableTrueTrueFalseTrueTrue{'a':1, 'b':2, 'c':3}
IteratorFalseFalseFalseTrueTrueFlase
from collections.abc import Iterable  # Import judgment module
from collections.abc import Iterator  # Import judgment module

# my = 'this_is_a_string'  # string
# my = [1, 2, 3, 4, 5]  # listd
# my = ('a', 'b', 'c', 'd', 'e')  # tuple
my = {'a': 1, 'b': 2, 'c': 3, 'd': 4, 'e': 5}  # dictionary
it = iter(my)  # Create iterator object


def f():    # generator function 
    yield 1


print(isinstance(it, Iterable))   # Determine whether it can be iterated
print(isinstance(it, Iterator))   # Determine whether it is an iterator
print(isinstance(my, Iterable))
print(isinstance(my, Iterator)) 
print(isinstance(f(), Iterable))
print(isinstance(f(), Iterator))

print("it Specific methods include:", dir(it))
print("my Specific methods include:", dir(my))
print("f()Specific methods include:", dir(f()))

>>>
True
True
True
False
True
True
it Specific methods include: ['__class__', '__delattr__', '__dir__', '__doc__', '__eq__', '__format__', '__ge__', '__getattribute__', '__gt__', '__hash__', '__init__', '__init_subclass__', '__iter__', '__le__', '__length_hint__', '__lt__', '__ne__', '__new__', '__next__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__', '__subclasshook__']
my Specific methods include: ['__class__', '__contains__', '__delattr__', '__delitem__', '__dir__', '__doc__', '__eq__', '__format__', '__ge__', '__getattribute__', '__getitem__', '__gt__', '__hash__', '__init__', '__init_subclass__', '__iter__', '__le__', '__len__', '__lt__', '__ne__', '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__setitem__', '__sizeof__', '__str__', '__subclasshook__', 'clear', 'copy', 'fromkeys', 'get', 'items', 'keys', 'pop', 'popitem', 'setdefault', 'update', 'values']
f()Specific methods include: ['__class__', '__del__', '__delattr__', '__dir__', '__doc__', '__eq__', '__format__', '__ge__', '__getattribute__', '__gt__', '__hash__', '__init__', '__init_subclass__', '__iter__', '__le__', '__lt__', '__name__', '__ne__', '__new__', '__next__', '__qualname__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__', '__subclasshook__', 'close', 'gi_code', 'gi_frame', 'gi_running', 'gi_yieldfrom', 'send', 'throw']


The difference between iterators and generators

  1. An iterator is a class; Generator is a function;
  2. Generator is a special iterator, which internally supports the generator protocol and does not need to be clearly defined__ iter__ () and next() methods;
  3. The generator is generated through the generator function. The generator function can be defined through the conventional def statement, but it does not return, but uses yield to return one result at a time.
  4. Both iterators and generators can be iterated through the for loop.

Topics: Python