【发布时间】:2015-06-19 21:41:43
【问题描述】:
我有一个大的 CSV 文件,我想将其拆分为一个等于系统中 CPU 内核数的数字。然后我想使用多进程让所有核心一起处理文件。但是,我什至无法将文件分成几部分。我查看了整个谷歌,发现一些示例代码似乎可以满足我的需求。这是我目前所拥有的:
def split(infilename, num_cpus=multiprocessing.cpu_count()):
READ_BUFFER = 2**13
total_file_size = os.path.getsize(infilename)
print total_file_size
files = list()
with open(infilename, 'rb') as infile:
for i in xrange(num_cpus):
files.append(tempfile.TemporaryFile())
this_file_size = 0
while this_file_size < 1.0 * total_file_size / num_cpus:
files[-1].write(infile.read(READ_BUFFER))
this_file_size += READ_BUFFER
files[-1].write(infile.readline()) # get the possible remainder
files[-1].seek(0, 0)
return files
files = split("sample_simple.csv")
print len(files)
for ifile in files:
reader = csv.reader(ifile)
for row in reader:
print row
这两个打印显示了正确的文件大小,并且它被分成了 4 个部分(我的系统有 4 个 CPU 内核)。
但是,打印每个片段中所有行的代码的最后一部分给出了错误:
for row in reader:
_csv.Error: line contains NULL byte
我尝试在不运行拆分功能的情况下打印行,它正确打印了所有值。我怀疑 split 函数在生成的 4 个文件片段中添加了一些 NULL 字节,但我不知道为什么。
有谁知道这是否是一种正确且快速的文件分割方法?我只想要 csv.reader 可以成功读取的结果片段。
【问题讨论】:
-
您的文件中有空字节吗?用 repr 打印行
-
我可以假设没有,因为打印原始文件的行而不拆分是成功的吗?
-
一个简单的方法是获取行数并将文件分成 n 片
-
您不能在任意点拆分 csv 文件,文件格式是面向行的,因此任何拆分都必须发生在行之间的边界处 — 这意味着您知道它们在哪里.
-
您确实要求拆分 CSV 文件并且已经有了答案。但是,您还给出了使用所有 CPU 内核的理由。有两点。您应该检查文件 I/O 或数字运算是否是您的瓶颈。你知道global interpreter lock?
标签: python csv split null byte