我想用python解析csv文件。为此,我想创建同一文件的副本,然后逐行解析。
如果其中一行符合条件,我希望从临时文件中删除该行,并将其放置到新文件中。
通过这种方式,我可以使tmp越来越小,因为它遍历列表,因此解析的次数较少,并且在解析结束时查看临时文件是否为空,并确认我的解析工作得很好。然而,我不会损坏原始文件。
让我们说原始文件包含:
AAAAAAAAAA
BBBBBBBBBB
CCCCCCCCCC
AAAAAAAAAA
BBBBBBBBBB
然后我有一个清单
list = [AAAAAAAAA, BBBBBBBBBB,CCCCCCCCCC]
我可以做以下几点:
for x in list:
for line in tmpCsv:
if x in line:
#remove line from tmpCsv place it to file x.CSV
答案 0 :(得分:2)
文件系统无法正常工作。您无法从磁盘上的文件中间有效地删除某些内容。为了模拟这个动作,操作系统首先复制文件中每个字节后面的删除行以掩盖“漏洞”,最后文件丢弃结束字节。以这种方式执行的每行删除都具有O(n)复杂度,其中n
是文件大小,并且删除所有行需要O(n 2 ) - 这很慢。
如果文件足够小,您可以读取整个文件并保留在内存中。如果它们太大而无法保存在RAM(千兆字节)中,请逐个读取并分别处理每个(如果可能的话)。
不需要删除匹配的行来执行您显然想要执行的操作。您可以只计算匹配的行数,如果数字为零则打印错误。
可以实现更高效的实施,但这应该适用于开始:
for x in list:
numberOfLinesMatched = 0
for line in tmpCsv:
if x in line:
numberOfLinesMatched += 1 # possibly break here
if numberOfLinesMatched == 0:
... # print an error, not found in the file
答案 1 :(得分:1)
据推测,解析后的数据将小于整个文件。因此,将较小的集合放在外部for循环上是正确的。但是你应该只需一次就可以做到这一点。下面我举一个潜在解决方案的例子。
这会逐行读取文件。如果该行符合第2段中描述的条件,则将其放在一个文件中。如果它不符合条件,则将其放在不同的文件中。
import os
if os.path.exists("match.csv") or os.path.exists("nonmatch.csv"):
raise False, "I AM NOT OVERWRITING A FILE"
originalCsv = open(csvFile,'r')
matchFile = open("match.csv","w"
nonmatchFile = open("nonmatch.csv","w"
while 1:
line = originalCsv.read()
if line == '': break
if line == meetsCondition:
nonmatchFile.writelines(line)
else:
matchFile.writelines(line)
matchFile.close()
nonmatchFile.close()
originalCsv.close()