我试图迭代一个非常大的、不断变化的文件(通常大约150万行),并对每一行执行操作。这是一个日志文件,因此在文件末尾追加新行。我的程序将允许用户指定每一行必须匹配的参数,并返回最近的匹配。因此,我希望从文件的末尾开始,并努力提高程序的效率(而不是列出一行代码并将其反转)。
下面是一个例子:
2016-01-01 01:00 apple
2016-01-02 05:00 banana
2016-01-03 03:00 apple
2016-01-04 00:00 apple
2016-01-05 12:00 banana
如果用户请求1行与"apple“匹配,我想返回"2016-01-04 00:00苹果”,这是最接近文件末尾的行。当只有五行时,这并不困难,但是当有数以百万计的行时,性能就会受到影响。我尝试使用tail -n [file size]
在文件末尾开始,但是这个方法不能很好地扩展;我不能使用迭代来提高性能(如果结果是文件中的最后一行,我不想迭代1,500,000行)。
我尝试过的另一种方法是将文件分解为“块”:
|
| Remaining lines
|
...
|
| Second group of n lines
|
|
| First group of n lines
|
然后,我将使用GNU sed
只流每个块中的行。然而,我发现程序的性能几乎没有改善(当n较小时,实际上受到了影响)。
是否有更好的方法(在迭代文件的同时最小化运行时间)?我一直在使用Linux命令行中的其他程序(通过“子进程”),但是使用Python内置的内容可能会更好。我非常感谢任何能引导我走向正确方向的信息。
我使用Linux访问Python2.7.3、2.7.10、2.7.11-c7、3.3.6和3.5.1。
发布于 2016-08-02 15:05:27
打开文件后,可以使用文件句柄的seek(bytes, start_point)
方法跳过文件中的任意位置,以若干字节表示。例如:
with open(my_file) as f:
f.seek(1024, 0)
for line in f:
print(line)
这将打印文件中的每一行,但第一个千字节除外。如果您提供了一个负数,它将返回,并且向第二个参数提供一个2
值将使它从文件的末尾开始计数。因此,调用f.seek(-1024, 2)
将导致上面只打印文件的最后一千字节。
当文件小于您的块大小时,可能需要一些安全措施来防止其死亡,但我就是这样做的。(如果您需要进一步追溯,这也非常简单:只需再次调用seek
即可。)
发布于 2016-08-02 15:08:22
您可以使用:
for line in reversed(open("filename").readlines()):
print line.rstrip()
在Python 3中:
for line in reversed(list(open("filename"))):
print(line.rstrip())
这里已经回答了这个问题:Read a file in reverse order using python
https://stackoverflow.com/questions/38723957
复制相似问题