python - 从协程接收器写入 csv 文件...如何避免文件关闭错误?

python - Writing to csv file out of coroutine sink ... how to avoid closed file error?

我的代码(简体):

import csv


def generate_record(downstream):
    try:
        while True:
            incoming = (yield)
            record = incoming.strip()
            for worker in downstream:
                worker.send(record)
    except GeneratorExit:
        for worker in downstream:
            worker.close()
        print('generate_record shutdown')


def file_writer(filename):
    l = list()    
    try:
        while True:
            record = (yield)
            l.append(record)
    except GeneratorExit:
        with open(filename, 'w', newline=''):
            writer = csv.writer(f)
            writer.writerows(l)
        print('file_writer shutdown')


if __name__ == '__main__':
    sink = file_writer('C:/Users/Some User/Downloads/data.csv')
    next(sink)    
    worker = generate_record([sink])
    next(worker)
    with open('C:/Users/Some User/Downloads/Energy.txt') as f:
        for line in f:
            worker.send(line)
    worker.close()

生成以下错误:

Traceback (most recent call last):

  File "<ipython-input-43-ff97472f6399>", line 1, in <module>
    runfile('C:/Users/Some User/Documents/Python Scripts/isii.py', wdir='C:/Users/Some User/Documents/Python Scripts')

  File "C:\Users\Some User\Anaconda3\lib\site-packages\spyderlib\widgets\externalshell\sitecustomize.py", line 699, in runfile
    execfile(filename, namespace)

  File "C:\Users\Some User\Anaconda3\lib\site-packages\spyderlib\widgets\externalshell\sitecustomize.py", line 88, in execfile
    exec(compile(open(filename, 'rb').read(), filename, 'exec'), namespace)

  File "C:/Users/Some User/Documents/Python Scripts/isii.py", line 75, in <module>
    worker.close()

  File "C:/Users/Some User/Documents/Python Scripts/isii.py", line 49, in generate_record
    worker.close()

  File "C:/Users/Some User/Documents/Python Scripts/isii.py", line 63, in file_writer
    writer.writerows(l)

ValueError: I/O operation on closed file.

我尝试了什么?

我尝试在 try 块中的 file_writer 中使用 writerow 进行增量写入,但这会产生相同的错误。

当您使用with open(filename) as f:时,它会执行您添加的操作,然后关闭文件。所以你不需要使用 worker.close() 因为你试图关闭一个已经关闭的文件。

参见:What is the python keyword "with" used for?

这应该是一个评论,但我似乎没有足够的声誉。

file_writer 中的 with 语句缺少 as f 部分;由于缺少它,f 引用了全局变量 f 而不是在撰写本文时关闭的全局变量;案例 IOError.

with open(filename, 'w', newline='') as f:
                                     ^^^^