我想从标准输入中读取一个 CSV 文件并处理每一行。我的 CSV 输出代码一一写入行,但我的读者在迭代行之前等待流终止。这是 csv
模块的限制吗?我做错了吗?
我的阅读器代码:
import csv
import sys
import time
reader = csv.reader(sys.stdin)
for row in reader:
print "Read: (%s) %r" % (time.time(), row)
我的作家代码:
import csv
import sys
import time
writer = csv.writer(sys.stdout)
for i in range(8):
writer.writerow(["R%d" % i, "$" * (i+1)])
sys.stdout.flush()
time.sleep(0.5)
python test_writer.py 的输出 | python test_reader.py
:
Read: (1309597426.3) ['R0', '$']
Read: (1309597426.3) ['R1', '$$']
Read: (1309597426.3) ['R2', '$$$']
Read: (1309597426.3) ['R3', '$$$$']
Read: (1309597426.3) ['R4', '$$$$$']
Read: (1309597426.3) ['R5', '$$$$$$']
Read: (1309597426.3) ['R6', '$$$$$$$']
Read: (1309597426.3) ['R7', '$$$$$$$$']
如您所见,所有打印语句同时执行,但我预计会有 500 毫秒的间隔。
最佳答案
正如它 says in the documentation ,
In order to make a
for
loop the most efficient way of looping over the lines of a file (a very common operation), thenext()
method uses a hidden read-ahead buffer.
您可以通过查看 the implementation of the csv
module 来查看(第 784 行)csv.reader
调用底层迭代器的 next()
方法(通过 PyIter_Next
)。
所以如果你真的想要无缓冲读取 CSV 文件,你需要将文件对象(这里是 sys.stdin
)转换成一个迭代器,它的 next()
方法实际上是改为调用 readline()
。这可以使用 iter
的两个参数形式轻松完成。功能。所以把 test_reader.py
中的代码改成这样:
for row in csv.reader(iter(sys.stdin.readline, '')):
print("Read: ({}) {!r}".format(time.time(), row))
例如,
$ python test_writer.py | python test_reader.py
Read: (1388776652.964925) ['R0', '$']
Read: (1388776653.466134) ['R1', '$$']
Read: (1388776653.967327) ['R2', '$$$']
Read: (1388776654.468532) ['R3', '$$$$']
[etc]
您能解释一下为什么需要无缓冲读取 CSV 文件吗?无论您尝试做什么,都可能有更好的解决方案。
关于python - 如何从流中读取 CSV 文件并在写入时处理每一行?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6556078/