在Python中,f.readlines()和list(f)有什么区别?

10 投票
1 回答
1732 浏览
提问于 2025-04-18 08:03

Python2 教程Python3 教程 中,第 7.2.1 节 的中间有一句话说:

如果你想把一个文件的所有行放到一个列表里,你可以使用 list(f) 或者 f.readlines()

所以我想问:这两种把文件对象转换成列表的方法有什么区别呢?我对它们的性能和底层的 Python 对象实现都很感兴趣(也许还有 Python2 和 Python3 之间的区别)。

1 个回答

14

从功能上来说,这两种方法没有区别;它们得到的列表是完全一样的。

从实现的角度来看,一种方法是把文件对象当作一个迭代器来使用(不断调用next(f),直到出现StopIteration),而另一种方法则是用专门的方法来读取整个文件。

在Python 2和3中,这两者的具体含义是有区别的,除非你在Python 2中使用io.open()。Python 2的文件对象使用了一个隐藏的缓冲区来进行文件迭代,如果你把文件对象的迭代和.readline().readlines()混在一起用,可能会出问题。

而在Python 3中,io库(负责处理所有文件的输入输出)并不使用这样的隐藏缓冲区,所有的缓冲都是由一个BufferedIOBase()包装类来处理的。实际上,io.IOBase.readlines()的实现在底层也是把文件对象当作迭代器来用的,而TextIOWrapper的迭代则委托给TextIOWrapper.readline(),所以list(f)f.readlines()实际上是一样的。

从性能上看,即使在Python 2中也没有真正的区别,因为瓶颈在于文件的输入输出;也就是你从磁盘读取数据的速度。在微观层面上,性能可能会受到其他因素的影响,比如操作系统是否已经缓存了数据,以及行的长度有多长。

撰写回答