我使用selenium进行网页抓取,然后尝试将数据存储到CSV文件中。我正在与工作人员一起使用队列,以便更快地进行抓取操作。
但是,我发现有时一个工作人员会写入CSV,然后另一个工作人员会尝试写入CSV,导致数据溢出到新行。
是否有一种安全的方法让多个工作人员同时写入CSV(或其他某种文件类型)?
这是我的工作人员和队列:
def worker():
while True:
params = q.get()
crawl(*params)
q.task_done()
q = Queue()
for i in range(7):
t = Thread(target=worker)
t.daemon = True
t.start()
每次'爬行'调用后,工作人员将一行写入CSV文件,然后关闭CSV:
data_fd = open('data.csv','a')
data_fd.write(line)
data_fd.close()
但是,当某个工作人员在另一个工作人员写完CSV之前尝试写入CSV时,有时会发生以下情况:
item_1, item_2, item_3, item_4
item_1, item_2, item_3,
item_1, item_2, item_3, item_4
item_4
答案 0 :(得分:2)
你可以采取两种不同的方法......
1)你"锁定"文件以某种方式 - 在操作系统级别上没有必要(你可以在写入文件之前获得一个监视器并在最后发布,这样在任何时候,只有一个线程持有监视器并写入文件)。
2)你可以拆分一个单独的线程专用于将数据写入csv。您的爬网程序线程会抓取数据并将其附加到队列中。 csv线程不断读取队列并将数据写入磁盘。
这两种方法都有其优点 - 第一种可能效率较低,但更容易处理。第二种方法需要考虑队列增长的大小(如果csv写入速度慢于抓取),并且在退出应用程序之前确保队列耗尽:)