为什么下面两行代码之间有区别?

2024-04-25 04:34:28 发布

您现在位置:Python中文网/ 问答频道 /正文

total = sum([float(item) for item in s.split(",")])


total = sum(float(item) for item in s.split(","))

资料来源:https://stackoverflow.com/a/21212727/1825083


Tags: inhttpscomfor来源floatitemstackoverflow
3条回答

第一种方法使用list comprehension构建所有浮点值的列表。你知道吗

第二种方法使用generator expression构建一个生成器,该生成器只根据请求构建每个浮点值,每次一个。当列表非常大时,这样可以节省大量内存。你知道吗

生成器表达式也可以更快(因为它允许工作流水线化,避免了内存分配时间)或更慢(因为它增加了一点开销),但这通常不是在两者之间进行选择的好理由。只需遵循以下简单的经验法则:

如果你需要一个列表(或者,更可能的是,只是一些你可以存储的东西,循环多次,打印出来等等),建立一个列表。如果你只需要循环这些值,不要建立一个列表。你知道吗

在这种情况下,很明显,您不需要列表,所以不要使用方括号。你知道吗


在Python2.x中,还有一些其他的细微差别;在3.x中,列表理解实际上定义为只调用生成器表达式上的list函数。(虽然至少在3.0-3.3中有一个小错误,但只有在您非常努力地查找时才能找到它……)

正如其他人所说,第一个创建一个列表,而第二个创建一个生成所有值的生成器。您可能关心这一点的原因是,创建列表会立即将所有元素放入内存,而使用生成器,您可以在生成元素时对它们进行处理,而不必将它们全部存储起来,这可能会影响到非常大的数据量。你知道吗

第一个是一个列表,而第二个是一个生成器表达式。在没有sum()函数调用的情况下尝试它们。你知道吗

In [25]: [float(a) for a in s.split(',')]
Out[25]: [1.23, 2.4, 3.123]

In [26]: (float(a) for a in s.split(','))
Out[26]: <generator object <genexpr> at 0x0698EF08>

In [27]: m = (float(a) for a in s.split(','))

In [28]: next(m)
Out[28]: 1.23

In [29]: next(m)
Out[29]: 2.4

In [30]: next(m)
Out[30]: 3.123

因此,第一个表达式首先在内存中创建整个列表,然后计算总和,而第二个表达式只获取表达式中的下一项并将其添加到当前的总和中。(内存效率更高)

相关问题 更多 >