如何使用多处理池读取文件
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了如何使用多处理池读取文件相关的知识,希望对你有一定的参考价值。
我想读取内容大约2GB的文件,我尝试使用多处理池来做,但它收到错误:
TypeError: 'type' object is not iterable
我知道map总是接受可迭代的参数,但有没有办法做到这一点?到目前为止,这是我的代码:
def load_embeddings(FileName):
#file = open(FileName,'r')
embeddings = {}
i = 0
print "Loading word embeddings first time"
for line in FileName:
# print line
tokens = line.split(' ')
tokens[-1] = tokens[-1].strip()
#each line has 400 tokens
for i in xrange(1, len(tokens)):
tokens[i] = float(tokens[i])
embeddings[tokens[0]] = tokens[1:-1]
print "finished"
return embeddings
if __name__ == "__main__":
t1 = time.time()
p = Pool(processes=5)
FileName = './asag/Resources/EN-wform.w.5.cbow.neg10.400.subsmpl.txt'
file_ = open(FileName,'r')
#fun = partial(load_embeddings,FileName)
result = p.map(load_embeddings, file_)
p.close()
p.join()
print ("Time it took :" + str(time.time() - t1))
答案
如果源代码在单进程环境中运行,那么它将是正确的。虽然你的论点FileName
应该命名为file
,因为它实际上是一个打开的文件句柄而不是文件名(字符串)。
现在,会发生的情况是,您正在为5个进程提供相同的文件句柄来处理。使用for line in FileName
,您可以对文件句柄执行读取操作。这在五个不同的过程中并行发生。所有人都不知道其他的(这是它的美丽:对于操作系统,这些是不同的程序运行。但它们都从相同的文件句柄读取)。现在,似乎这不是原子的,只有部分读取行后才能中断此调用。也可以,python在内部缓冲,但缓冲区是每个进程。这导致line
中的半行或第一行的部分和第二行的部分(因为python只读到它看到第一个
)然后当你想要进一步处理该行时你会得到错误。
要解决此问题,您需要先在主进程中读取文件,然后将这些行交给map
函数,如下所示:
from multiprocessing import Pool
def load_embeddings(line):
embeddings = {}
i = 0
tokens = line.split(' ')
tokens[-1] = tokens[-1].strip()
#each line has 400 tokens
for i in xrange(1, len(tokens)):
tokens[i] = float(tokens[i])
embeddings[tokens[0]] = tokens[1:-1]
print "finished"
return embeddings
if __name__ == "__main__":
p = Pool(processes=5)
file_name = 'file.tsf'
lines = []
with open(file_name,'r') as f:
for line in f:
lines.append(line.strip())
result = p.map(load_embeddings, lines)
p.close()
p.join()
以上是关于如何使用多处理池读取文件的主要内容,如果未能解决你的问题,请参考以下文章