如何使用lxml,XPath和Python从网页中提取链接?

时间:2010-01-18 08:22:26

标签: python screen-scraping hyperlink lxml extraction

我有这个xpath查询:

/html/body//tbody/tr[*]/td[*]/a[@title]/@href

它会使用title属性提取所有链接,并在FireFox's Xpath checker add-on中提供href

但是,我似乎无法将其与lxml一起使用。

from lxml import etree
parsedPage = etree.HTML(page) # Create parse tree from valid page.

# Xpath query
hyperlinks = parsedPage.xpath("/html/body//tbody/tr[*]/td[*]/a[@title]/@href") 
for x in hyperlinks:
    print x # Print links in <a> tags, containing the title attribute

这不会产生lxml(空列表)的结果。

如何在Python下抓取包含href属性标题的超链接的lxml文本(链接)?

2 个答案:

答案 0 :(得分:10)

我能够使用以下代码:

from lxml import html, etree
from StringIO import StringIO

html_string = '''<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
   "http://www.w3.org/TR/html4/loose.dtd">

<html lang="en">
<head/>
<body>
    <table border="1">
      <tbody>
        <tr>
          <td><a href="http://stackoverflow.com/foobar" title="Foobar">A link</a></td>
        </tr>
        <tr>
          <td><a href="http://stackoverflow.com/baz" title="Baz">Another link</a></td>
        </tr>
      </tbody>
    </table>
</body>
</html>'''

tree = etree.parse(StringIO(html_string))
print tree.xpath('/html/body//tbody/tr/td/a[@title]/@href')

>>> ['http://stackoverflow.com/foobar', 'http://stackoverflow.com/baz']

答案 1 :(得分:3)

Firefox adds additional html tags到呈现时的html,使firebug工具返回的xpath与服务器返回的实际html不一致(以及urllib / 2将返回的内容)。

删除<tbody>标记通常可以解决问题。