Python readlines() 用法和高效读取的实践

8 浏览
0 Comments

Python readlines() 用法和高效读取的实践

我有一个问题,需要解析一个文件夹中的数千个文本文件(每个文件大约有400KB大小的3000行左右)。我使用readlines方法读取了它们,代码如下:

for filename in os.listdir(input_dir):
    if filename.endswith(".gz"):
        f = gzip.open(file, 'rb')
    else:
        f = open(file, 'rb')
    file_content = f.readlines()
    f.close()
    
len_file = len(file_content)
while i < len_file:
    line = file_content[i].split(delimiter)
    # ...我的逻辑...
    i += 1

对于样本输入(50,100个文件),这个方法完全正常运行。但是当我在整个输入上运行时(超过5000个文件),所花费的时间并没有线性增加。我计划进行性能分析,并进行了Cprofile分析。随着输入文件数量的增加,所需时间呈指数级增长,当输入达到7000个文件时,速度变得更差。

下面是readlines方法的累计时间消耗:

第一次:354个文件(输入样本)

第二次:7473个文件(整个输入)

ncalls  tottime  percall  cumtime  percall filename:lineno(function)
354    0.192    0.001    **0.192**    0.001 {method 'readlines' of 'file' objects}
7473 1329.380    0.178  **1329.380**    0.178 {method 'readlines' of 'file' objects}

因此,由于这个原因,我的代码所花费的时间并没有随着输入的增加而线性增长。我阅读了一些关于readlines方法的文档,其中有人声称readlines方法会将整个文件内容读入内存,因此通常比readline或read方法消耗更多内存。

我同意这一点,但是垃圾回收器应该会在循环结束时自动清除加载的内容,因此在任何时刻,我的内存中应该只有当前处理的文件内容,对吗?但是,这里有一些问题。有人可以对这个问题提供一些见解吗?

这是readlines方法的固有行为,还是我对Python垃圾回收器的错误解读?希望了解。同时,建议一些在内存和时间上更高效的替代方法。谢谢。

0