【问题标题】:Python selenium loop getting slower and slowerPython selenium 循环越来越慢
【发布时间】:2020-09-14 13:36:08
【问题描述】:

我正在尝试抓取一个评论网站(类似于 Trustpilot)。 首先,我得到了一个大约 50k 的 url 链接列表(抱怨)来抓取。然后,我从每个 url/complain 中抓取特定数据。

问题是,我的 forloop 越来越慢。它开始每 3 秒抓取一个 url,但现在它的速率是 20 秒/迭代。

有人可以检查我的代码并指出潜在的缺陷吗?

Tks

for url in tqdm(urls):
    driver.get(url)
    count +=1
    try:
        df_load = pd.DataFrame({'id' : [counta],
         'caption' : [driver.find_element_by_xpath(
            '//*[@id="complain-detail"]/div/div[1]/div[2]/div/div[1]/div[2]/div[1]/h1').text],
         'details': [driver.find_element_by_xpath(
            '//*[@id="complain-detail"]/div/div[1]/div[2]/div/div[1]/div[2]/div[1]/ul[1]').text],
         'status' : [driver.find_element_by_xpath(
            '//*[@id="complain-detail"]/div/div[1]/div[2]/div/div[1]/div[2]/div[3]/span[2]/strong').text],
         'complaint' : [driver.find_element_by_xpath(
            '//*[@id="complain-detail"]/div/div[1]/div[2]/div/div[2]/p').text]})
        df = pd.concat([df_load, df])
    except:
        print(f'ID {counta} did not work')
        pass

【问题讨论】:

  • 您需要在正在抓取的页面上渲染 JavaScript,还是只是解析 HTML?
  • 我尝试使用 scrapy 直接解析 html 但没有成功(网站返回我运行的是过时的浏览器,尽管随机分配了用户代理)。
  • 好的,所以 Selenium 可能是正确的选择。您使用的是哪个网络驱动程序?
  • chrome, v85 (和我的浏览器一样)
  • 尝试使用 PhantomJS(不会产生显示网页的开销)如果它有效我可以将其发布为答案。你可以在这里找到一个很好的介绍:realpython.com/…

标签: python selenium loops


【解决方案1】:

在数据帧上使用 concat 非常缓慢且占用大量内存,每次调用时,都会返回数据帧的新副本。有关详细信息,请参阅此处的回复:

Why does concatenation of DataFrames get exponentially slower?

【讨论】:

  • tks。我应该考虑将抓取的数据附加到循环下的列表中
  • 没错!在循环内的每次迭代中附加到一个列表,一旦循环完成,您就可以连接列表。
  • tks 院长。任何想法如何进一步加速此代码?我正在尝试抓取 50k + url 大声笑
  • 是否需要使用selenium来抓取具体数据?如果没有,我会考虑使用 Requests 和 BeautifulSoup
  • 我尝试使用 scrapy 直接解析 html 但没有成功(网站返回我运行的是过时的浏览器,尽管随机分配了用户代理)。