【问题标题】:Python library to do jQuery-like text extraction?Python 库进行类似 jQuery 的文本提取?
【发布时间】:2011-05-24 12:19:38
【问题描述】:

我的 html 包含这样的条目:

<div class="entry">
  <h3 class="foo">
    <a href="http://www.example.com/blog-entry-slug"
    rel="bookmark">Blog Entry</a>
  </h3>
  ...
</div>

我想提取文本“博客条目”(以及许多其他属性,所以我正在寻找一个通用的答案)。

在 jQuery 中,我会这样做

$('.entry a[rel=bookmark]').text()

我在 Python 中最接近的是:

from BeautifulSoup import BeautifulSoup
import soupselect as soup

rawsoup = BeautifulSoup(open('fname.html').read())

for entry in rawsoup.findAll('div', 'entry'):
    print soup.select(entry, 'a[rel=bookmark]')[0].string.strip()

soupselect from http://code.google.com/p/soupselect/.

Soupselect 不像 jQuery 那样理解完整的 CSS3 选择器语法。 Python中有这样的野兽吗?

【问题讨论】:

    标签: jquery python css-selectors beautifulsoup


    【解决方案1】:

    您可能还想看看 pyquery。 pyquery 是一个类似 jquery 的 python 库。 找到它here

    【讨论】:

      【解决方案2】:

      BeautifulSoup 允许(基本)CSS 选择器:http://www.crummy.com/software/BeautifulSoup/bs4/doc/#css-selectors

      但是,如果您需要更精细的 CSS 选择器,他们会在文档中引用 lxml (http://lxml.de/)。

      【讨论】:

        【解决方案3】:

        您可能想看看lxmlCSSSelector 类,它尝试按照w3c 规范中的描述实现CSS 选择器。作为旁注,manyfolksrecommendlxml 现在用于通过 BeautifulSoup 解析 HTML/XML,出于性能和其他原因。

        我认为 lxml 的 CSSSelector 使用 XPath 进行元素选择,但您可能需要自己查看文档。这是您使用 lxml 的示例:

        >>> from lxml.cssselect import CSSSelector
        >>> from lxml.html import fromstring
        >>> html = '<div class="entry"><h3 class="foo"><a href="http://www.example.com/blog-entry-slug" rel="bookmark">Blog Entry</a></h3></div>'
        >>> h = fromstring(html)
        >>> sel = CSSSelector("a[rel=bookmark]")
        >>> [e.text for e in sel(h)]
        ['Blog Entry']
        

        【讨论】:

        • 由于某种原因,这对我不起作用(fromstring 似乎需要有效的 html lol),但是您提供的链接之一将我引向了 pyquery。 pyquery 的动机是“嘿,让我们在 python 中制作 jquery”,从我的初步测试中,我已经能够依靠我对 jQuery 的了解而不是阅读文档(!)
        • 对格式错误的 html 使用“from lxml.html import fromstring”
        【解决方案4】:

        使用关键字参数真的很容易。

        >>> from BeautifulSoup import BeautifulSoup
        >>> soup = BeautifulSoup('''<div class="entry">
        ...   <h3 class="foo">
        ...     <a href="http://www.example.com/blog-entry-slug"
        ...     rel="bookmark">Blog Entry</a>
        ...   </h3>
        ...   ...
        ... </div>
        ... ''')
        >>> soup.find('div', 'entry').find(rel='bookmark').text
        u'Blog Entry'
        

        或者,

        >>> for entry in soup('div', 'entry'):
        ...     for bookmark in entry(rel='bookmark'):
        ...         print bookmark.text
        ...
        Blog Entry
        

        您也可以使用attrs 来影响.entry 而不是div.entry 的选择器:

        >>> for entry in soup(attrs={'class': 'entry'}):
        ...     for bookmark in entry(rel='bookmark'):
        ...         print bookmark.text
        ...
        Blog Entry
        

        (注意调用汤或汤的一部分相当于.findAll()。)

        作为一个列表理解,这是[b.text for e in soup('div', 'entry') for b in e(rel='bookmark')](产生[u'Blog Entry'])。

        如果你想要真正的 CSS3 选择器,我不知道 BeautifulSoup 有什么这样的东西。所有(或几乎所有)都可以通过简单的嵌套、条件和正则表达式来完成(你也可以使用entry(rel=re.compile('^bookmark$')))。如果您想要类似的东西,请将其视为您的下一个项目!它对于扁平化代码和让网络人更容易理解很有用。

        【讨论】:

        • 看起来还不错。我在使用 BeautifulSoup 时遇到的问题是,我每次使用它时都必须重新学习界面。我更频繁地使用 jQuery,这就是为什么我在寻找类似的东西。
        • 这真的很简单。大多数情况下,您只需要findAll(tag_name, class_name, attr1=value) 等,其值为None 表示未设置,True 表示已设置,str 表示来自re.compile 的值或正则表达式。然后只需使用普通的 Python 迭代结构。它与 CSS 选择器不同,但不难理解和记住,并且在某些情况下提供了更多功能。
        猜你喜欢
        • 2011-03-04
        • 2020-05-18
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多