首页 > 代码库 > Python之路----------生成器
Python之路----------生成器
一、列表生成式
想想如何创建一个列表[0,1,2,3,4,5]
1 l = [0,1,2,3,4,5]
如果上面的列表元素足够多的话,是不是会写很多代码?看看列表生成式怎么写
1 #列表生成式 2 l = [x for x in range(6)] 3 4 #上面的代码相当于 5 l = [] 6 for x in range(6): 7 l.append(x) 8 9 #用列表生成式可以节省代码,快速生成列表
二、生成器(generator)
什么是生成器?
通过列表生成式,我们可以直接创建一个列表。但是,受到内存限制,列表容量肯定是有限的。而且,创建一个包含100万个元素的列表,不仅占用很大的存储空间,如果我们仅仅需要访问前面几个元素,那后面绝大多数元素占用的空间都白白浪费了。
所以,如果列表元素可以按照某种算法推算出来,那我们是否可以在循环的过程中不断推算出后续的元素呢?这样就不必创建完整的list,从而节省大量的空间。在Python中,这种一边循环一边计算的机制,称为生成器(Generator)。
生成器只有在调用时才会生成相应的数据,生成器只记录当前位置并且生成器只有一个__next__()方法,但是一般不用next方法都用循环去调用生成器。
1 import time 2 a = time.time() 3 l = [x for x in range(30000000)] 4 b = time.time() 5 print(b-a) 6 7 a = time.time() 8 g = (x for x in range(30000000)) 9 b = time.time() 10 print(b-a) 11 12 13 #l列表生成时间会很久,也很占内存,而g是用生成器没有耗时(原因是生成器调用才有数据)
斐波那契数列
斐波那契数列(Fibonacci sequence),又称黄金分割数列、因数学家列昂纳多·斐波那契(Leonardoda Fibonacci)以兔子繁殖为例子而引入,故又称为“兔子数列”,指的是这样一个数列:1、1、2、3、5、8、13、21、34、……在数学上,斐波纳契数列以如下被以递归的方法定义:F(1)=1,F(2)=1, F(n)=F(n-1)+F(n-2)(n>2,n∈N*)在现代物理、准晶体结构、化学等领域,斐波纳契数列都有直接的应用,为此,美国数学会从1963起出版了以《斐波纳契数列季刊》为名的一份数学杂志,用于专门刊载这方面的研究成果。
1 def fib(max): 2 n, a, b = 0, 0, 1 3 while n < max: 4 print(b) 5 a, b = b, a + b 6 n = n + 1
生成器函数版本:
1 def fib(max): 2 n, a, b = 0, 0, 1 3 while n < max: 4 yield b 5 a, b = b, a + b 6 n = n + 1
三、生成器牛逼的用法
生成器并行计算(简单的生产者消费者模型)异步IO模型雏形
1 #coding=utf-8 2 import time 3 from random import choice 4 5 def producer(): 6 mooncake = ["五仁馅", "咸蛋黄馅", "黑芝麻馅", "青红丝馅", "猪肉馅", "咸鱼馅"] 7 c = consumer(‘Mr.A‘) 8 c1 = consumer(‘Mis.B‘) 9 c.__next__() 10 c1.__next__() 11 print("食品厂开始生产月饼了") 12 n = 0 13 while n < 3: 14 time.sleep(1) 15 mooncake1 = choice(mooncake) 16 print("食品厂生产了%s月饼" % mooncake1) 17 c.send(mooncake1) 18 mooncake2 = choice(mooncake) 19 print("食品厂生产了%s月饼" % mooncake2) 20 c1.send(mooncake2) 21 n += 1 22 23 def consumer(name): 24 print("%s 准备开始吃月饼了" % name) 25 while True: 26 mooncake = yield 27 print("%s吃掉了%s月饼" % (name, mooncake)) 28 29 producer()
Python之路----------生成器