提前感谢您的帮助。
我是Python的新手,我正在尝试将文件从一种格式转换为另一种格式。
这是我的代码:
fs = open('sample_data.txt','r')
fnew = open('sample_output.txt','w')
with fs as f:
while True:
line = f.readline()
if line and line[0]=='#':
print(line)
fnew.write(line + '\n')
else:
data=line.split()
fnew.write(data[0])
if not line: break
print('end of program')
fs.close
fnew.close
文件的基本格式在顶部包含注释标题,后跟数据行。
我遇到的问题是我的fnew.write(data [0])行。我收到以下错误:
IndexError:列表索引超出范围
分割线分解了八列数据,其中我要删除前两列。所以,最终,我想要做的是重写整个文件减去前两列。我需要做一些更复杂的重新格式化,但我希望如果我能理解这一步中的错误,我可能会想出如何完成其余的工作。
-------------- UPDATE
abarnet,你是对的。这是导致错误的换行符。但是,在尝试添加支票时,我遇到了另一个问题,就像你说的那样。当我执行下面的代码时,一切都冻结在我身上。如果我删除“if data:”检查,那么它会运行,但会给我相同的“索引超出范围”错误。我还尝试按下面的方法运行它,删除了“if data:”检查,并且使用了一个不包含换行符的示例数据文件,它也冻结了我。
任何人都可以解释可能造成这种情况的原因吗?
fs = open('sample_data.txt','r')
fnew = open('sample_output.txt','w')
with fs as f:
while True:
line = f.readline()
for line in f:
if line[0]=='#':
print(line)
fnew.write(line + '\n')
else:
data=line.split()
if data:
print(data[0])
fnew.write(data[0] + '\n')
print('end of program')
fs.close
fnew.close
--------------更新2
以下代码有效。感谢abarnet澄清无限循环问题。我遇到的最后一个问题是数据的第一行,无论是换行还是标题行都被忽略,并且不会在输出中打印。
with open('sample_data.txt','r') as f, open('sample_output.txt','w') as fnew:
line = f.readline()
for line in f:
if line[0]=='#':
print(line)
fnew.write(line + '\n')
else:
data=line.split()
if data:
print(data[0])
fnew.write(data[0] + '\n')
print('end of program')
fnew.close()
答案 0 :(得分:1)
首先,如果line
为空,会发生什么?
您最终会到达if not line: break
。但是在你到达那里之前,你将会到达第一个else:
(因为line and line[0]=='#'
并非如此)。因此,您的data = line.split()
会给您data = []
。然后data[0]
会提出IndexError
。
首先移动if not line: break
测试:
while True:
line = f.readline()
if not line:
break
elif line[0]=='#':
print(line)
fnew.write(line + '\n')
else:
data=line.split()
fnew.write(data[0])
话虽如此,首先要写一个更简单的方法。循环遍历文件将逐个给出每一行,就像while
周围的readline
循环一样,除了当它到达EOF时,循环自动结束而不需要测试任何内容或{{ 1}}。
break
但如果行不是为空,如果它只是空白或纯空白,会发生什么?例如,当您在for line in f:
if line[0]=='#':
print(line)
fnew.write(line + '\n')
else:
data=line.split()
fnew.write(data[0])
上致电split()
时会发生什么?再次,你得到一个空列表。所以,如果可能的话,你又会遇到同样的问题 - 当然,在这种情况下你可能不想' \n'
。我不确定你想做什么,但是让我们说你想跳过空白链接。所以只需将break
块替换为:
else
作为旁注,在第一种情况下执行data=line.split()
if data:
fnew.write(data[0])
非常奇怪,其中该行已在fnew.write(line + '\n')
中结束,因此您只需添加额外的换行符,但在另一种情况下为\n
,其中fnew.write(data[0])
并未在换行符中结束,因此您只需将第一列的一行合并为一个巨大的单词与下一个评论到底......
新代码的问题在于,您使用data[0]
循环代替替换<{em> while True:
readline()
周围的for line in f:
循环两个
所以,第一次通过while
循环,它读取第一行,然后读取文件中的每一行,然后完成。然后,第二次通过while
循环,它读取结尾处剩下的所有内容,然后读取剩下的所有0行,然后结束。它会一直持续下去,一遍又一遍地阅读最后的0行,直到时间结束,因为你永远不会break
出while True:
。
您的更新代码中还有一些其他问题。
fs.close
只是引用方法,而不实际调用它。您需要括号来进行通话,例如fs.close()
。fs.close()
; with
语句的重点在于它会自动关闭文件。with
使用fnew
语句。所以:
with open('sample_data.txt','r') as f, open('sample_output.txt','w') as fnew:
for line in f:
if line[0]=='#':
print(line)
fnew.write(line + '\n')
else:
data=line.split()
if data:
print(data[0])
fnew.write(data[0] + '\n')
print('end of program')