我有一个包含900万个http链接的列表,它们存储在lt
中
对于最小可重复的example:
我最初写的是
cat = []
i=0
for l in lt:
print(i)
if re.search('.+videoStory.+', l):
print('video')
cat.append('video')
else:
response=requests.get(l,headers = { 'User-Agent': 'Mozilla/5.0 (Windows NT 6.1) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/41.0.2228.0 Safari/537.36', })
if response.status_code == 200:
bs = BeautifulSoup(response.content.decode('ascii', 'ignore'),'lxml')
cat.append(bs.findAll('div', {'class':'ArticleHeader_channel_4KD-f'})[0].text)
elif response.status_code == 404:
print('404')
cat.append('404')
elif response.status_code == 500:
print('500')
cat.append('500')
else:
print(response.status_code)
break
i+=1
bs.findAll('div', {'class':'ArticleHeader_channel_4KD-f'})[0].text
提取页面的类别。这段代码在1秒钟内成功完成了3个链接,这意味着要获得900万个链接需要34.7天(通过仅花费5000个链接花费27分钟左右的时间进行测试)
p = pool.Pool(1000)
yo= []
jobs=[]
def get_link(ul):
if re.search('.+videoStory.+', ul):
yo.append('video')
else:
r = requests.get(ul, headers = { 'User-Agent': 'Mozilla/5.0 (Windows NT 6.1) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/41.0.2228.0 Safari/537.36', })
if r.status_code == 200:
bs = BeautifulSoup(r.content.decode('ascii', 'ignore'),'lxml')
crap = bs.findAll('div', {'class':'ArticleHeader_channel_4KD-f'})[0].text
yo.append(crap)
elif r.status_code == 404:
# print('404')
yo.append('404')
elif r.status_code == 500:
# print('500')
yo.append('500')
startTime= datetime.now()
for yum in lt:
jobs.append(p.apply_async(get_link, args =(yum,)))
gevent.joinall(jobs)
timeElapsed=datetime.now()-startTime
print('Time elpased (hh:mm:ss.ms) {}'.format(timeElapsed))
这段代码在1秒钟内成功完成了5个链接,这意味着要获得900万个链接需要20.8天(通过仅花费5000个链接花费16分钟左右的时间进行测试)
这花了太长时间。
应该尝试将
concurrency
设置为10000
,这会有所帮助吗?(也许路透社不允许同时允许这么多)我应该尝试并行处理吗?
最佳答案
有了这些信息,您应该能够运行代码的多个实例,这些实例从列表中的不同位置开始。
假设您运行5个代码实例,每个实例都负责通过5,000个链接。因此,一次运行即可覆盖25,000个链接。这对您来说大约是30分钟。
假设实例1在链接1-5000中运行,当其列表用尽时,它应从第25,001个链接开始。因此,对于每个实例,您都必须对其进行迭代以从第where_it_left + 25000
个链接运行。
让我们在这里看看数学。简单的例子:5,000,000 links / 25,000 = 200 runs.200 * 0.5 hour = 100 hours (~ 4-5 days)
如果一次可以运行5个以上的代码实例,则甚至可以进一步减少此开销。
另一个更好的方法是使用HTTrack等网络抓取软件。但是,您可能必须对其进行大量配置才能根据需要获得结果。
关于python - Gevent Pool似乎并没有提高性能,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/47103401/