【问题标题】:Making a basic web scraper in Python with only built in libraries - Python仅使用内置库在 Python 中制作基本的网络爬虫 - Python
【发布时间】:2013-08-10 00:38:25
【问题描述】:

学习 Python,我正在尝试制作一个没有任何 3rd 方库的网络爬虫,这样我的过程就不会简化,而且我知道自己在做什么。我浏览了几个在线资源,但所有这些都让我对某些事情感到困惑。

html 看起来像这样,

<html>
<head>...</head>
<body>
    *lots of other <div> tags*
<div class = "want" style="font-family:verdana;font-size:12px;letter-spacing:normal"">
<form class ="subform">...</form>
<div class = "subdiv1" >...</div>
<div class = "subdiv2" >...</div>
    *lots of other <div> tags*
</body>
</html>

我希望爬虫提取 &lt;div class = "want"...&gt;*content*&lt;/div&gt; 并将其保存到 html 文件中。

我对如何解决这个问题有一个非常基本的想法。

import urllib
from urllib import request
#import re
#from html.parser import HTMLParser

response = urllib.request.urlopen("http://website.com")
html = response.read()

#Some how extract that wanted data

f = open('page.html', 'w')
f.write(data)
f.close()

【问题讨论】:

  • 我可以理解我不想使用一个为你做所有事情的网络抓取库......但你可能想考虑使用 BeautifulSoup 只是用于解析部分。如果 HTML 都是现代且有效的,那么您应该可以在 stdlib 中使用它,但如果您需要处理古怪的现实页面,BS 会让您的生活更轻松。 (即使对于简单的情况,它也稍微简单一些,但这没什么大不了的。)

标签: python web-scraping extract extraction


【解决方案1】:

标准库自带各种Structured Markup Processing Tools,你可以用它来解析HTML,然后搜索它来提取你的div。

那里有很多选择。你用什么?

html.parser 看起来是显而易见的选择,但实际上我会从 ElementTree 开始。这是一个非常好的和非常强大的 API,整个网络上有大量的文档和示例代码可以帮助您入门,并且每天都有很多专家使用它来帮助您解决问题。如果结果证明 etree 无法解析您的 HTML,您将不得不使用其他东西……但请先尝试。

例如,通过对您的 HTML 进行一些小的修复,它实际上是有效的,因此实际上有一些文本值得从您的 div 中取出:

<html>
<head>...</head>
<body>
    *lots of other <div /> tags*
<div class = "want" style="font-family:verdana;font-size:12px;letter-spacing:normal">spam spam spam
<form class ="subform">...</form>
<div class = "subdiv1" >...</div>
<div class = "subdiv2" >...</div>
    *lots of other <div /> tags*
</div>
</body>
</html>

您可以使用这样的代码(我假设您知道或愿意学习 XPath):

tree = ElementTree.fromstring(page)
mydiv = tree.find('.//div[@class="want"]')

现在您已经获得了对 div 类 "want" 的引用。您可以通过以下方式获取其直接文本:

print(mydiv.text)

但如果你想提取整个子树,那就更简单了:

data = ElementTree.tostring(mydiv)

如果您想将其包含在有效的 &lt;html&gt; 和 &lt;body&gt; 中和/或删除 &lt;div&gt; 本身,则必须手动完成该部分。该文档解释了如何使用简单的树 API 构建元素:创建一个 head 和一个 body 以放入 html,然后将 div 粘贴到 body 中,然后将 tostring html,仅此而已。

【讨论】:

  • 我之前忘了提到我曾经尝试过XPath,但是不知道如何使用它,哈哈。您的代码与上面的 HTML 示例完美配合(如预期的那样)。然而,当我在我试图抓取的网站上尝试这个时,似乎我得到了一个xml.etree.ElementTree.ParseError: not well-formed (invalid token) error。现在我猜这是因为网站的 HTML 没有得到正确验证。猜猜这是把我推到汤边:P
  • 如果您不确定该站点是否有效,您可能需要使用在线 HTML 验证器进行检查。 (有无数个;只需搜索一个。)此外,即使它是有效的,请注意 HTML(XHTML 和 HTML5 的 XML 呈现除外)实际上不是有效的 XML,因此不能保证像这样的 XML 解析库ElementTree 将处理它。实际上,大多数有效的 HTML 4.01 strict 和 HTML5,以及许多 4.01 过渡版都可以使用,但不是全部(早期版本不太可能使用)。
  • 那么你推荐什么是更有效的替代方法(:
  • @Red:这取决于问题所在。但是安装和使用beautifulsoup4 几乎总是解析可能无效的 HTML 或 XML 的最佳答案。您可能还想安装html5lib 和/或lxml(不要直接使用它们,而是让BeautifulSoup 使用)。您仍在编写您想编写的部分,只是使用比标准库中的解析器更智能的解析器。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-05-12
  • 1970-01-01
  • 1970-01-01
  • 2014-10-29
相关资源
最近更新 更多