第一篇文章, 尽可能地批评...
我的问题: 我有一个1.4亿行(文件1)的大文件和300万行(文件2)的稍小文件。我想删除文件1中与文件2匹配的那些行。直观地说,这似乎是一个简单的查找和删除问题,不应该花费那么长的时间。相对而言。正如我的代码在24Gb处理器上运行大约需要4天。我想在几个文件上执行此操作,因此我希望能够及时改进。 任何帮助和评论将不胜感激。
示例文件1:
reftig_0 43 0 1.0
reftig_0 44 1 1.0
reftig_0 45 0 1.0
reftig_0 46 1 1.0
reftig_0 47 0 5.0
示例文件2:
reftig_0 43
reftig_0 44
reftig_0 45
代码:
data = open('file_1', 'r')
data_2 = open('file_2', 'r')
new_file = open('new_file_1', 'w')
d2= {}
for line in data_2:
line= line.rstrip()
fields = line.split(' ')
key = (fields[0], fields[1])
d2[key]=1
#print d2.keys()
#print d2['reftig_1']
tocheck=d2.keys()
tocheck.sort()
#print tocheck
for sline in data:
sline = sline.rstrip()
fields = sline.split(' ')
nkey = (fields[0],fields[1])
#print nkey
if nkey in tocheck:
pass
else:
new_file.write(sline + '\n')
#print sline
答案 0 :(得分:4)
使用grep
grep -Fvf file2 file1
答案 1 :(得分:4)
您的脚本很慢,因为行if nkey in tocheck
正在针对 nkey
检查list
。这非常非常慢,因为它是线性搜索(即使tocheck
已排序)。
改为使用set
:
def getkey(line):
line = line.rstrip()
fields = line.split(' ')
return (fields[0], fields[1])
tocheck = {getkey(line) for line in data_2}
for line in data:
if getkey(line) not in tocheck:
new_file.write(line)
将它与unutbu的写入批处理相结合,你的脚本运行得非常快。
答案 2 :(得分:3)
每行将短字符串写入new_file
一次很慢。通过将内容附加到列表来减少写入次数,并仅在列表长度为1000行时写入new_file
。
N = 1000
with open('/tmp/out', 'w') as f:
result = []
for x in range(10**7):
result.append('Hi\n')
if len(result) >= N:
f.write(''.join(result))
result = []
以下是针对time test.py
的各种值运行N
的结果:
| N | time (sec) |
| 1 | 5.879 |
| 10 | 2.781 |
| 100 | 2.417 |
| 1000 | 2.325 |
| 10000 | 2.299 |
| 100000 | 2.309 |