Dan*_*Eng 1 python multiprocessing web-scraping
我想使用多处理模块来加速网页抓取。我的目标是在页面中提取一部分 HTML 并将其保存在父变量中。最后,将该变量写入文件。
但我遇到的问题是处理页面大约需要 1 秒。
我的代码有效,但它没有做我想要的:
import urllib.request
from bs4 import BeautifulSoup
from multiprocessing.dummy import Pool # This is a thread-based Pool
from multiprocessing import cpu_count
def parseWeb(url):
page = urllib.request.urlopen(url)
soup = BeautifulSoup(page)
h2_tag = soup.find('h2', class_='midashigo')
return h2_tag
if __name__ == '__main__':
file = 'links.txt' # each link is on a separate line.
pool = Pool(cpu_count() * 2)
with open(file, 'r') as f:
results = pool.map(parseWeb, f)
with open('output.txt', 'w', encoding='utf-8') as w:
w.write(str(results))
Run Code Online (Sandbox Code Playgroud)
如何修改它以赋予它多处理的全部功能?谢谢你。
这个过程应该是 I/O 绑定的,这意味着你的瓶颈应该是在解析之前你可以拉下多少连接,但实际上它可能会被 CPU 或内存绑定。
您需要意识到的第一件事是多线程/处理不会加快单个页面的解析时间。因此,如果一页需要一秒钟,而您有 420000 页,则需要 420000 秒。如果您将线程数增加到您的 PC 的内核数量的两倍,并且您的 PC 有 4 个内核,那么您将有 8 个线程每页运行 1 秒。您仍然以 420000 / 8 秒结束,即 875 分钟(实际上这并不完全正确),这是 14.5 小时的处理时间....
为了使时间跨度易于管理,您将需要大约 400 个线程,这将使处理时间减少到理论上的 17 多分钟。
有这么多线程在运行,页面被解析,内存也将成为一个问题。
我把这个小应用程序放在一起测试了几次
from time import sleep
from multiprocessing.dummy import Pool
from multiprocessing import cpu_count
def f(x):
sleep(1)
x = int(x)
return x *x
if __name__ == '__main__':
pool = Pool(cpu_count() * 100)
with open('input.txt', 'r') as i:
results = pool.map(f, i)
with open('output.txt', 'w') as w:
w.write(str(results))
Run Code Online (Sandbox Code Playgroud)
对于数字 1 到 420 000 的输入文件,处理时间花费了 1053.39 秒(大约 17.5 分钟),但这并不能很好地指示您需要多长时间,因为上述内存和 I/O 受到限制问题,你最终可能会得到明显更慢的东西。
底线是,如果您没有最大限度地利用 CPU、RAM 或网络 I/O,那么您的线程池就太小了。
| 归档时间: |
|
| 查看次数: |
3476 次 |
| 最近记录: |