1
Python 生成器的问题
source link: https://www.v2ex.com/t/787076
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.
学习 python 生成器的时候遇到一个问题, 生成器的目的是减少空间占用, 所以每次只是返回一个值. 再有通项公式的时候我能理解, 每一项实际上都可以算出来这样就不用记录全部的元素了. 但是如果我随便找一个没有规律的 list 做成生成器, 那么空间的节约体现在哪里呢? 比如我有这样的代码
(x for x in [1,5,-1,10])
假设我的这个 list 是没有规律的, 那么这个生成器是不是要存下来整个的 list, 那么空间的节约体现在哪里?
11 条回复 • 2021-07-02 12:46:19 +08:00
yufpga 2 小时 11 分钟前
首先生成器的目的并不是为了减少空间占用。其次你要搞明白生成器的原理, 就绕不开理解 yield 的机制。(x for x in [1,5,-1,10]) 等价于:
def gen():
for i in [1, 5, -1, 10]:
yield i
g = gen()
def gen():
for i in [1, 5, -1, 10]:
yield i
g = gen()
yufpga 1 小时 55 分钟前
@wuwukai007
@HashV2
我并没有在解释节省内存的问题,我在说的是生成器的原理,解释元祖形式的列表生成器的本质。
可以去看看 python 生成器的 PEP ( https://www.python.org/dev/peps/pep-0255/), 该有的里面都有.
事实上,你们也看到,生成器不一定总是会减少内存占用
@HashV2
我并没有在解释节省内存的问题,我在说的是生成器的原理,解释元祖形式的列表生成器的本质。
可以去看看 python 生成器的 PEP ( https://www.python.org/dev/peps/pep-0255/), 该有的里面都有.
事实上,你们也看到,生成器不一定总是会减少内存占用
abersheeran 42 分钟前
你的场景不对。
比如你要处理一个 31Gb 的文件,你电脑却只有 16G 内存,该怎么办呢?这时候用 yield file.read(4096) 进行流式处理。就能大幅度节约内存空间。
比如你要处理一个 31Gb 的文件,你电脑却只有 16G 内存,该怎么办呢?这时候用 yield file.read(4096) 进行流式处理。就能大幅度节约内存空间。
BeautifulSoap 27 分钟前
谈生成器不谈迭代器的话你当然搞不清楚这么搞是为什么
生成器的一个目的是方便遍历啊,一些情况下的确可以省内存,但是重点是方便遍历啊,方便遍历啊(重要的说三遍
迭代器通过统一了__next__()和__iter__()两个接口,可以让使用者不用在乎你内部结构多么复杂,你只要用 iter()和 next()这两个方法都可以轻松遍历。并且学过迭代器的人难道忘了么,你一直习以为常在用的 `for i in xxxx` 这写法实际上就是个语法糖 iter()和 next()写法的语法糖啊。省内存只不过是迭代器带来的优点之一,根本目的还是统一了接口可以让你轻松遍历对象
然后就是生成器,生成器可以部分看作是迭代器的语法糖(虽然 yield 作用不止是语法糖),你手写迭代器需要实现__next__()和__iter__()两个接口,而用 yield 构建的生成器只需要简单几行代码就行了,生成器和迭代器一样可以使用 next()迭代,也能用 `for in xxx` 这个语法糖,所以,本质上还是为了方便遍历啊
生成器的一个目的是方便遍历啊,一些情况下的确可以省内存,但是重点是方便遍历啊,方便遍历啊(重要的说三遍
迭代器通过统一了__next__()和__iter__()两个接口,可以让使用者不用在乎你内部结构多么复杂,你只要用 iter()和 next()这两个方法都可以轻松遍历。并且学过迭代器的人难道忘了么,你一直习以为常在用的 `for i in xxxx` 这写法实际上就是个语法糖 iter()和 next()写法的语法糖啊。省内存只不过是迭代器带来的优点之一,根本目的还是统一了接口可以让你轻松遍历对象
然后就是生成器,生成器可以部分看作是迭代器的语法糖(虽然 yield 作用不止是语法糖),你手写迭代器需要实现__next__()和__iter__()两个接口,而用 yield 构建的生成器只需要简单几行代码就行了,生成器和迭代器一样可以使用 next()迭代,也能用 `for in xxx` 这个语法糖,所以,本质上还是为了方便遍历啊
Recommend
About Joyk
Aggregate valuable and interesting links.
Joyk means Joy of geeK