我的目标是构建一个日志解析器,它将复制我想要的关键字之间所选的关键字,并将其写入文件。因为我必须在单个文件中搜索多个关键字,所以我想编写一个函数并在脚本中多次使用它。
但是,我无法通过以下脚本并得到一个错误来实现这一点:
import re
def myfunc (infile ,outfile, search1 , search2):
fi = infile.readlines()
fo = open(outfile, 'w')
write1 = False
for line in fi:
if re.findall('search1' , str(line)):
write1 = True
elif re.findall('search2', str(line)):
write1 = False
elif write1:
fo.write(line)
fo.close()
fi.close()
return;
text_file = open(input("name of inputfile : "))
resultfile = input("name of outputfile : ")
search1 = "teen"
search2 = "eight"
myfunc (text_file , resultfile , search1 , search2)我收到以下错误:
Traceback (most recent call last):
File "C:/Users/zoro/PycharmProjects/text-parsing/write selected test 2 sets.py", line 38, in <module>
myfunc (text_file , resultfile , search1 , search2)
File "C:/Users/zoro/PycharmProjects/text-parsing/write selected test 2 sets.py", line 28, in myfunc
fi.close()
AttributeError: 'list' object has no attribute 'close'发布于 2015-09-22 08:16:56
fi = infile.readlines()这使得fi成为文件infile中的一行列表。因此,当您稍后调用fi.close()时,您将尝试关闭一个列表,这当然不起作用。
相反,您需要关闭文件,即infile
infile.close()一般来说,以一种方式更改变量名是个好主意,这样它们包含的内容就很明显了。infile是您读取的文件对象,所以没关系。outfile是要写入的文件的文件名,因此您应该将其命名为outFileName或其他什么。fi是infile中的一行列表,所以您应该称它为inFileLines。
您还应该避免手动关闭文件对象;相反,使用with语句确保它们自动关闭:
with open(outfile, 'w') as fo:
fo.write('stuff')
# no need to manually close it最后,您的代码还有另一个问题:re.findall('search1' , str(line)) --它将搜索行中的字符串'search1';它将不尊重传递给函数并存储在search1 (和search2)变量中的值。因此,您需要删除引号:re.findall(search1, line) (您也不需要将行转换为字符串)。
另外,如果您只评估它的真值,那么使用re.findall()并不是最好的方法。相反,使用re.search,它只返回第一个结果(因此对于非常长的行,如果已经找到结果,就不会继续搜索)。如果search1和search2不包含实际的正则表达式,而只包含想要在行中找到的字符串,那么还应该使用in运算符:
if search1 in line:
write1 = True最后一个注意事项:文件句柄应该始终从打开的同一级别关闭。因此,如果在函数中打开文件句柄,那么该函数也应该关闭它。如果您在函数外部打开一个文件,则该函数不应该关闭它。关闭文件是打开程序的责任,对于其他情况,关闭文件可能会导致错误的行为,因此您不应该这样做(除非明确记录了它,例如,函数doSomethingAndClose可能关闭文件)。
使用with语句通常可以避免这种情况,因为您从不手动调用file.close(),而且with语句已经确保文件正确关闭。
如果您想多次使用一个文件,那么您必须使用寻求开始才能再次读取它。在您的示例中,由于使用infile.readlines()将整个文件读入内存,所以最好只从文件中读取一行,然后将其用于多个函数调用:
text_file = input("name of inputfile : ")
with open(text_file) as infile:
fi = infile.readlines() # read the lines *once*
myfunc(fi, …)
myfunc(fi, …)
myfunc(fi, …)https://stackoverflow.com/questions/32711502
复制相似问题