iter(fp.readline,'')中的行,而不是fp中的行:

时间:2018-09-21 14:59:24

标签: python python-3.x iterator file-handling

我在Built-in Functions — Python 3.7.0 documentation中阅读了内置函数iter的示例

with open('mydata.txt') as fp:
    for line in iter(fp.readline, ''):
        process_line(line)

我不知道与以下内容相比有什么优势:

with open('mydata.txt') as fp:
    for line in fp:
        process_line(line)

请提供任何提示吗?

2 个答案:

答案 0 :(得分:2)

两者都将迭代生成器,而不将整个文件加载到内存中,但是iter()版本说明了iter()的第二个参数“ sentinel”的使用。

从文档中

  

如果返回的值等于哨兵,则会引发StopIteration

因此该代码将从文件中读取,直到一行等于'',然后停止。

这是一个奇怪的示例,因为文件中的所有行的末尾都有换行符,因此无论如何(如果有的话)只会在文件末尾触发。

答案 1 :(得分:0)

正如我和wim在评论中所讨论的,在这种情况下,没有优势。要使第二个代码片段与第一个代码片段等效,则它将类似于以下内容:

with open('mydata.txt') as fp:
    for line in fp:
        if line == '':
            break
        process_line(line)

但是,readline可以返回空字符串的唯一情况是在文件(EOF)的末尾,因此现在在这里有所不同(其他行至少包含换行符'\n') )。

如果不是使用空字符串,而是使用另一个值,那么区别将是有意义的。就个人而言,我认为文档应该使用一个更好的示例来说明这一点,如下所示:

>>> f = open('test')
>>> f.read()
'a\nb\nc\n\nd\ne\nf\n\n'
>>> f = open('test')
>>> [line for line in iter(f.readline, 'b\n')]
['a\n']
>>> f = open('test')
>>> [line for line in f]
['a\n', 'b\n', 'c\n', '\n', 'd\n', 'e\n', 'f\n', '\n']

(请注意,我确实应该关闭文件句柄)

编辑:我在issue34764

中提出了这是一个可能的文档错误。