文件迭代,检查行存在性
我正在用一个循环来读取一个文件,像这样...
f = open("somefile.txt")
for line in f:
do stuff
但是每次我读取一行时,我需要从下一行取一个项目,然后把它放到当前这一行里。有什么好的方法可以做到这一点吗?有没有办法在不读取下一行的情况下获取它的某个项目?
4 个回答
0
如果你的文件可以放进内存里,你可以试试下面的做法:
f = open('somefile.txt')
lines = f.read().splitlines()
for current_line, next_line in zip(lines, lines[1:]):
print current_line
print next_line
print '-------'
上面的代码基本上是读取所有的行,然后用 zip
函数把当前行和下一行组合成一个个小组(元组)。
补充说明:如果文件很长,你可以使用 itertools
库,方法如下:
import itertools
f = open('somefile.txt')
i1, i2 = itertools.tee(f)
lines = itertools.izip(i1, itertools.islice(i2, 1, None))
for current_line, next_line in lines:
print current_line
print next_line
print '-------'
在这种情况下:
itertools.tee
用来创建两个独立的迭代器(一个用来处理当前行,另一个用来处理下一行),它们都使用原始的文件迭代器。itertools.slice
用来让第二个迭代器从第二行开始。itertools.izip
用来把两个迭代器的结果逐行组合成元组。
补充说明2:正如 @eyquem 提到的,你也可以打开文件两次:
import itertools
f = open('somefile.txt')
g = open('somefile.txt')
lines = itertools.izip(f, itertools.islice(g, 1, None))
for current_line, next_line in lines:
print current_line
print next_line
print '-------'
3
如果你的文件不大,可以把它全部读到内存里,然后在里面处理:
f = open("somefile.txt")
lines = f.readlines()
f.close()
for index, value in enumerate(lines):
# Check if next line exists
if index + 1 > len(lines):
next_line = lines(index + 1)
# do something with line and next_line
补充:
对于大文件,最简单的方法就是记住你之前那一行:
f = open("somefile.txt")
previous_line = f.readline()
for line in f:
# Do something with line and previous_line
print(line, previous_line)
# Save this line for the next iteration
previous_line = line
根据你的数据情况,可能会有一些特殊情况。比如说,你的行数据是总是成对出现,还是在某些情况下只需要下一行的一点信息。
举个例子,如果你的文件只有一行,这段代码就不会有任何作用。
7
如果我理解得没错,你想要逐行处理数据,并且需要用到下一行的一些值。我的建议是,先把你当前正在处理的值存起来,然后用上一个值来进行操作。也就是说,反着来——last_line
是你当前处理的行,而“行”就是下一行。
last_line = None
with open("somefile.txt") as f:
for line in f:
if not last_line == None:
do_stuff(last_line, extract_needed_part(line))
last_line = line
do_stuff(last_line) #The final line without anything following it.
用数学的说法来说,就是不要用第n行和第n+1行,而是用第n-1行和第n行,效果是一样的。
这种方法的好处是,你不需要一开始就把整个文件都加载进来。