Iterators and generators based on Python

Refer to "Python3 from entry to actual combat"

One, iterator

1. The __iter() method of an iterable team image returns an iterator, and the __next () method of this iterator returns the next element of the iterable object.
Note: the iterable object can be output with for in , And iterators use the next method ()

2.Python provides two corresponding built-in functions iter() and next(). The built-in function iter() acts on an iterable object. It will call the object’s __iter__() method to return an iterator, and the built-in function next() ) Acting on this iterator, it will call the __next()__ method brought up by this to return the next element of the iterable element

	alist = [1,3,5,19,7]
    it = iter(alist)#返回一个迭代器
    print(type(alist))
    print(type(it))
    print(next(it))#得到迭代器的下一个值
    运行结果如下:
    <class 'list'>
	<class 'list_iterator'>
	1

The following class A implements the __iter__() method, so the object of class A is an iterable object, and the method of iter () must return an iterator, that is, the object of class B must be an iterator, that is to say, class B Must implement __next__() method

	import time
    class A(object):
        def __iter__(self):
            return B()
        
    class B(object):
        def __next__(self):
            return "hello"
        
    iterable = A()#可迭代对象   可迭代对象由下列方法进行迭代
    iterator = iter(iterable)#迭代器 迭代器用next方法
    
    #一直打印hello
    i = 0
    for e in iterable:
        print(e)
        time.sleep(1)
        print(i)
        i += 1

	运行结果如下:
	hello
	0
	hello
	1
	hello
	2
	hello
	3
	hello
	#需要自己按下停止按钮,这里没有设置什么时候停止,而是一个死循环
	class A(object):
        def __iter__(self):
            return B()
        
    class B(object):
        def __init__(self):
            self.i = 0
            self.data = [2,4,8]
        def __next__(self):
            if self.i == 3:#计数,到3就停止执行
                raise StopIteration()
            self.i += 1
            return self.data[self.i-1]#返回每个值
    
    iterable = A()
    for e in iterable:
        print(e,end=" ")

	运行结果如下:
	2 4 8 

3. Generally, the class of the iterable object and the class of the iterator are not completely separated in this way, but the same class. This class implements the __iter__() and __next__() methods at the same time, so even this type of object An iterable object is also an iterator

	class X(object):
        def __init__(self):
            self.i = 0
            self.data = [2,4,8]
        def __iter__(self):
            return self
        def __next__(self):
            if self.i == 3:
                raise StopIteration()
            self.i += 1
            return self.data[self.i-1]
    b = X()
    
    it = iter(b)#得到迭代器
    
    print(next(it))
    #print(next(it))
    
    b2 = X()
    
    for i in b2:
        print(i)
    运行结果如下:
    2
	2
	4
	8

4. An object is iterable. In addition to its class implementing the __iter__() method, its class can also implement the __getitem__() method

5. If you use a for loop to output an infinite loop, the second parameter is a key (keyword). For the class object obj that implements this method, you can get the value corresponding to the key through obj[key]

	class Y:
        def __getitem__(self,i):
            return i * i
    y = Y()
    
    print(y[2])


	运行结果如下:
	4
	class MyDict:
        def __init__(self):
            self.dict = {
    
    }
        def __getitem__(self,key):
            return self.dict[key]
        def __setitem__(self,key,value):
            self.dict[key] = value
        def __len__(self):
            return len(self.dict)
    d = MyDict()
    d['李萍'] = 67.5#调用setitem方法
    print(d['李萍'])#调用getitem方法
    d['王伟'] = 77.5
    print(d['王伟'])
	运行结果如下:
	67.5
	77.5

Second, the generator

1. The generator is a simple and powerful tool for creating iterators. It is also a function that can generate a series of values. The generator will remember the last executed statement. Whenever data is needed, the generator will start from Continue at the interruption and generate a new data through the yield statement. Therefore the generator is a special iterator and an iterable object

Generator function

	def gen(n):
        for i in range(n):
            yield(i)
    
    '''生成器会记住函数执行的状态,当再次调用__next__()方法时,
    会根据上次的位置和状态,继续执行,当再次遇到yield语句,
    又产生一个新的返回值并终止当前的执行.
    '''     
    g = gen(5)
    print(g.__next__())
    print(g.__next__())
    print(next(g))#也可以用这种方法(因为生成器也是迭代器)
    print(g)#g是一个生成器的对象
    print(type(g))
    #迭代
    g = gen(10)#生成器是一个可迭代对象
    for i in g:
        print(i)

	运行结果如下:
	0
	1
	2
	<generator object gen at 0x000002335EEF0A50>
	<class 'generator'>
	0
	1
	2
	3
	4
	5
	6
	7
	8
	9

2. The function containing return will stall the function execution and return when it encounters the return statement. Each execution of the function is independent and starts from the beginning. The state and position of the previous execution will not be saved.

3. The generator function containing the yield is used to generate a series of values. Each time it is executed, the yield statement will stop execution and return the result of the yield statement, but the state of the previous execution will be retained internally, and the next execution will start from the previous The code after the executed yield continues to execute until it encounters yield again and returns

4. The generator function can be used to generate a series of values, these values ​​are not stored in the memory, but generated when needed, which can save a lot of memory

	#求1到10的整数和
    #生成器方法
    def gen(n):
        for i in range(n):
            yield i
            
    g = gen(11)#这是一个生成器
    
    sum = 0
    for e in g:
        sum += e
    print(sum)

	运行结果:
	55
	#用生成器产生斐波拉西数列
    def fib(M):
        n,a,b = 0,0,1
        while(n<M):
            yield b 
            a,b = b,a+b#这个是同时完成a=b,b=a+b
            n += 1
            
    for x in fib(8):
        print(x,end=" ")
	
	运行结果如下:
	1 1 2 3 5 8 13 21 

Three, the iterative tool of the standard library

1.zip function, the input parameter of this function is any number of variable iterable objects, and returns a data element (tuple iterator), each tuple is composed of corresponding elements in multiple input iterators

2. If there are no input parameters, an empty iterator is returned

3. If an iterable object is input, a data element (tuple's iterator) is returned, and each tuple has only one value

4. If multiple iterable objects are input, a data element (tuple's iterator) is returned, and each tuple is composed of object elements from the input iterable object.

5. The zip object is an iterable object, so you can use it to construct a list object, but you cannot use it to construct a tuple object

	result = zip()
    print(list(result))
    alist = [1,2,3]
    result = zip(alist)
    for e in result:
        print(e,end=" ")
        
    print()
    str = ("许嵩","周杰伦","薛之谦")
    result = zip(alist,str)
    for e in result:
        print(e)


	运行结果如下:
	[]
	(1,) (2,) (3,) 
	(1, '许嵩')
	(2, '周杰伦')
	(3, '薛之谦')

	a = [1,2,3]
    b = ['a','b','c']
    c = zip(a,b)#用zip将a,b打包
    c = list(c)#要有这句话,否则报错
    for i in c:
        print(i)
        
    d,e = zip(*c)#用zip将a,b解包
    print(d,e)

	运行结果如下:
	(1, 'a')
	(2, 'b')
	(3, 'c')
	(1, 2, 3) ('a', 'b', 'c')

6.The function enumerate, inputs an iterable object, and returns an enumerate object, which is also an iterable object, each element of which is shaped like (index, value)

7. The function chain() returns an iterable object that connects multiple iterable objects in series

	import itertools#需要先导入这个模块
    it1 = [1,2,3]
    it2 = (2,3,4)
    it = itertools.chain(it1,it2)
    for e in it:
        print(e)
    运行结果如下:
    '''
    1
    2
    3
    2
    3
    4
    '''

8. Function count() This function returns an iterator, which generates a uniform sequence of numbers. The starting value of the sequence is start, and the difference between two adjacent ones is step. This sequence is an infinite sequence

	from itertools import count
    
    for i in count(10):#start=10 默认step=1
        if i > 20:
            break
        print(i)
    '''
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    '''

9.The function islice() is also a function of itertools, the function format is as follows:

islice(iterable,stop)
islice(iterable,start,stop[,step])

This function is used to generate a slice object from the iterable object, where stop is the end position of the slice, start is the start position, and step is the step size

	from itertools import islice,count
    
    #2即是步长
    #count(10)是一个迭代器
    for i in islice(count(10),5,10,2):#第五个开始,到第十个,step=2
        print(i)

	运行结果如下:
    '''
    15
    17
    19
    '''

10. The function cycle() acts on an iterable object to produce an iterator of values ​​in the iterable object that repeats the loop

	from itertools import cycle
    count = 0
    for item in cycle('xyz'):
        if count > 9:
            break
        print(item,end=" ")
        count += 1
    '''
    x y z x y z x y z x 
    '''

11.#Function repeatThis function is used to generate a time iterator with repeated values ​​of object. The difference between it and the function cycle() is that it only acts on a valued object object, while the function cycle() acts on one Iterable object with multiple values

	from itertools import repeat
    
    r = repeat(7,3)#重复一个对象 多少次
    for i in r:
        print(i)
    '''
    7
    7
    7
    '''

Summary: This article introduces the use of iterators and generators, you can easily iterate some objects if you master it.

Guess you like

Origin blog.csdn.net/qq_45911278/article/details/111814446