【问题标题】:Read previous line in a file python读取文件python中的上一行
【发布时间】:2013-06-26 17:21:50
【问题描述】:

当我遍历文件时,我需要获取文件中前一行的值并将其与当前行进行比较。该文件很大,因此我无法完整读取它或使用linecache 随机访问行号,因为库函数仍然会将整个文件读入内存。

编辑很抱歉,我忘了提到我必须向后读取文件。

EDIT2

我尝试了以下方法:

 f = open("filename", "r")
 for line in reversed(f.readlines()): # this doesn't work because there are too many lines to read into memory

 line = linecache.getline("filename", num_line) # this also doesn't work due to the same problem above. 

【问题讨论】:

  • 你的意思是前一行?不能边走边保存吗?
  • 如果您向我们展示您目前所写的内容,您将更有可能获得帮助。
  • 你能提供你试过的东西吗?可以逐行遍历文件,并且可以将行分配给变量,那么到底出了什么问题?顺便问一下,HUGE 有多大?
  • 我不能,因为文件有太多行,所以当我尝试将它们全部放入列表时,python 抱怨它无法为列表分配必要的内存。
  • 如果您仍然按顺序访问这些行,您是否尝试过一次存储两个连续的行?

标签: python file loops


【解决方案1】:

当你迭代到下一个时,只需保存上一个

prevLine = ""
for line in file:
    # do some work here
    prevLine = line

这将在您循环时将上一行存储在 prevLine 中

edit 显然 OP 需要向后读取此文件:

aaand 经过一个小时的研究,我在内存限制内多次失败

Here你去 Lim,那家伙知道他在做什么,这是他最好的主意:

通用方法#2:读取整个文件,存储行的位置

使用这种方法,您还可以通读整个文件一次,但是 而不是将整个文件(所有文本)存储在内存中,您只需 将二进制位置存储在每行开始的文件中。 您可以将这些位置存储在与第一个相似的数据结构中 在第一种方法中存储行。

无论你想读取第 X 行,你必须从 文件,从您为该行的开头存储的位置开始。

优点:几乎与第一种方法一样容易实施 缺点:可以采用 一段时间来读取大文件

【讨论】:

  • 非常感谢。但是我忘了提到我必须向后读取文件。
  • 魔术。我是 python 新手,所以虽然我知道文件是可迭代的,但我从未想过使用 [::-1] 。谢谢。
  • 您无法对文件进行切片,因此您编辑的代码没有任何意义。
  • @Stephan:我刚试过这个,在[::-1] 部分出现类型错误:TypeError: 'file' object has no attribute '__getitem__'。这是 Python 2.7 与 Python 3.0 的问题吗?还是您以特定方式打开文件?我正在使用 Python 2.7,并以 my_file = open("file.txt","r") 的身份打开我的文件
  • @Stephan 对不起,我认为你的话是理所当然的,但我刚刚尝试发现你不能对文件进行切片。
【解决方案2】:

@Lim,我会这样写(回复 cmets)

def do_stuff_with_two_lines(previous_line, current_line):
    print "--------------"
    print previous_line
    print current_line

my_file = open('my_file.txt', 'r')

if my_file:
    current_line = my_file.readline()

for line in my_file:

    previous_line = current_line
    current_line = line

    do_stuff_with_two_lines(previous_line, current_line)

【讨论】:

  • 谢谢。非常抱歉,但我忘了提到我必须向后读取文件。
【解决方案3】:

我会为这个任务写一个简单的生成器:

def pairwise(fname):
    with open(fname) as fin:
        prev = next(fin)
        for line in fin:
            yield prev,line
            prev = line

或者,您可以使用来自itertools 的pairwise 配方:

def pairwise(iterable):
    "s -> (s0,s1), (s1,s2), (s2, s3), ..."
    a, b = itertools.tee(iterable)
    next(b, None)
    return itertools.izip(a, b)

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2017-06-15
    • 2018-08-05
    • 1970-01-01
    • 1970-01-01
    • 2015-04-07
    • 2021-10-28
    • 2018-02-25
    相关资源
    最近更新 更多