簡體   English   中英

產生多個進程以編寫不同的文件Python

[英]spawn multiple processes to write different files Python

這個想法是使用N進程寫入N文件。

要寫入文件的數據來自多個文件,這些文件存儲在一個字典中,該字典具有一個作為值的列表,看起來像這樣:

dic = {'file1':['data11.txt', 'data12.txt', ..., 'data1M.txt'],
       'file2':['data21.txt', 'data22.txt', ..., 'data2M.txt'], 
        ...
       'fileN':['dataN1.txt', 'dataN2.txt', ..., 'dataNM.txt']}

所以file1data11 + data12 + ... + data1M等...

所以我的代碼看起來像這樣:

jobs = []
for d in dic:
    outfile = str(d)+"_merged.txt"
    with open(outfile, 'w') as out:
        p = multiprocessing.Process(target = merger.merger, args=(dic[d], name, out))
        jobs.append(p)
        p.start()
        out.close()

和merge.py看起來像這樣:

def merger(files, name, outfile):
    time.sleep(2)
    sys.stdout.write("Merging %n...\n" % name)

    # the reason for this step is that all the different files have a header
    # but I only need the header from the first file.
    with open(files[0], 'r') as infile:
        for line in infile:
            print "writing to outfile: ", name, line
            outfile.write(line) 
    for f in files[1:]:
        with open(f, 'r') as infile:
            next(infile) # skip first line
            for line in infile:
                outfile.write(line)
    sys.stdout.write("Done with: %s\n" % name)

我確實看到該文件寫在應該去的文件夾上,但是它是空的。 沒有頭,什么都沒有。 我把照片放在那里,看一切是否正確,但沒有任何效果。

救命!

由於工作進程與創建它們的主進程並行運行,因此命名out的文件將在工作進程寫入之前關閉。 即使由於with語句而刪除out.close() ,也會發生這種情況。 而是向每個進程傳遞文件名,然后讓進程打開和關閉文件。

問題是您沒有在子級中關閉文件,因此內部緩沖的數據會丟失。 您可以將文件移動給孩子,也可以將整個文件包裝在try / finally塊中,以確保文件關閉。 在父級中打開的潛在優勢是您可以在那里處理文件錯誤。 我並不是說它具有吸引力,只是一種選擇。

def merger(files, name, outfile):
    try:
        time.sleep(2)
        sys.stdout.write("Merging %n...\n" % name)

        # the reason for this step is that all the different files have a header
        # but I only need the header from the first file.
        with open(files[0], 'r') as infile:
            for line in infile:
                print "writing to outfile: ", name, line
                outfile.write(line) 
        for f in files[1:]:
            with open(f, 'r') as infile:
                next(infile) # skip first line
                for line in infile:
                    outfile.write(line)
        sys.stdout.write("Done with: %s\n" % name)
    finally:
        outfile.close()

UPDATE

關於父/子文件解密器以及子文件中的文件發生了什么混亂。 如果程序退出時文件仍處於打開狀態,則基礎C庫不會將數據刷新到磁盤。 從理論上講,正確運行的程序會在退出之前關閉事物。 這是一個示例,在該示例中,孩子丟失了數據,因為它沒有關閉文件。

import multiprocessing as mp
import os
import time

if os.path.exists('mytestfile.txt'):
    os.remove('mytestfile.txt')

def worker(f, do_close=False):
    time.sleep(2)
    print('writing')
    f.write("this is data")
    if do_close:
        print("closing")
        f.close()


print('without close')
f = open('mytestfile.txt', 'w')
p = mp.Process(target=worker, args=(f, False))
p.start()
f.close()
p.join()
print('file data:', open('mytestfile.txt').read())

print('with close')
os.remove('mytestfile.txt')
f = open('mytestfile.txt', 'w')
p = mp.Process(target=worker, args=(f, True))
p.start()
f.close()
p.join()
print('file data:', open('mytestfile.txt').read())

我在linux上運行它

without close
writing
file data: 
with close
writing
closing
file data: this is data

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM