概述
生成器
通过列表,可以包含很多很多的元素,但是受到内存的制约,列表的内容一定是有限的。它无法表达无限的内容。比如说,全部的正整数,就不可能被放到一个列表之中去使用。但是,全部的正整数确实是应当可以被用作使用的,因为只需要通过前一个元素,就能够推断出后一个元素了。
因此,在这种情况下,我们有了一种新的东西,就是生成器,也就是generator。生成器无需一下子保存或读取出全部的内容,只需要在需要用到的时候,生成一个,就可以了。
生成器生成式
之前,我们提到了列表推导式,实际上,只要将列表推导式中的[]改为(),就可以创建一个生成器了。如果模仿列表生成式或者列表推导式的名字的话,也许我们应当称之为生成器生成式或者生成器推导式,不过这种说法似乎不是很常见。
注:关于列表推导式,有的时候我称呼其为列表推导式,有的时候我又称呼其为列表生成式,是因为这两种称呼非常通用,使用哪一种都是一样的,所以,就没有为了统一性,而选择只使用其中的一种说法。如果你觉得哪一种说法更好的话,可以自行使用其中的一种。
比如说,之前我们写过这样一个列表生成式,我们将其改为生成器生成式。
# 这是之前使用过的一个关于九九乘法表的列表推导式
li = ["%s * %s = %s" % (i, j, i * j) for i in range(1, 10) for j in range(1, 10) if i <= j]
# 将[]改为()以后,可以直接变成生成器
g_li = ("%s * %s = %s" % (i, j, i * j) for i in range(1, 10) for j in range(1, 10) if i <= j)
# 打印以后,我们可以看出,这是一个generator
print(g_li)
我们可以发现,直接打印一个生成器,是不可以的,因为它是在使用的过程中,才被生成的,因此,我们必须通过next()或者for循环的形式,去使用一个生成器。
# 每使用一次next(),就会新生成一个元素
print(next(g_li))
print(next(g_li))
print(next(g_li))
print(next(g_li))
# 使用for循环,可以通过遍历得到所有的元素
for i in g_li:
print(i)
创建详细的生成器
虽然通过生成器生成式已经可以创建出生成器,但是,生成式的方式毕竟是一种比较简单的方式,面对一些复杂的需求的话,生成器难以应对。因此,我们可以通过函数定义的形式,得到一个生成器。
这里,我们需要使用一个关键字yield,当函数执行到yield时,会得到yield的内容,并且停止运行,当下一次调用的时候,会从上一次的yield开始继续运行,并执行到下一次yield再次暂停。
比如说,定义一个简单的生成器
# 通过函数,定义生成器
def g_num(x):
for i in range(x):
# 当执行到yield i的时候,会生成i,并且暂停
# 当下一次调用的时候,会从这里继续运行,到下一个yield再次暂停
yield i
注意,此时g_num不是一个生成器,g_num是一个函数。当这个函数被调用的时候,我们得到的是一个生成器。我们可以像这样使用。
# 生成器的使用
for i in g_num(100):
print(i)
# 如果你不希望使用生成器,也可以通过list()
# 以此来将生成器直接转换为一个列表
a = list(g_num(10))
# 但是需要注意的是,不是所有的生成器都能够被转换为列表的
# 比如以下代码中,生成器是可以直接获取到的,但是如果你要将其转换为列表
# 可能就会失败或者使计算机陷入一些困境之中
x1 = g_num(1000000000000)
x2 = list(g_num(1000000000000))
总结
虽然通过next()或者for循环两种方式都可以使用生成器,但是一般来说,不会真的手动通过next()调用的。使用for循环来配合生成器使用要更多一些。
最后
以上就是淡然小海豚为你收集整理的python中使用生成器生成器生成器生成式创建详细的生成器总结的全部内容,希望文章能够帮你解决python中使用生成器生成器生成器生成式创建详细的生成器总结所遇到的程序开发问题。
如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。
发表评论 取消回复