BeautifulSoup只获取td标记中的“常规”文本,而嵌套标记中没有任何内容

时间:2015-07-07 17:06:00

标签: python beautifulsoup

说我的html看起来像这样:

<td>Potato1 <span somestuff...>Potato2</span></td>
...
<td>Potato9 <span somestuff...>Potato10</span></td>

我有美丽的做法:

for tag in soup.find_all("td"):
    print tag.text

我得到了

Potato1 Potato2
....
Potato9 Potato10

是否可以只获取标签内的文本,而不是嵌套在span标签内的任何文本?

2 个答案:

答案 0 :(得分:6)

您可以使用.contents作为

>>> for tag in soup.find_all("td"):
...     print tag.contents[0]
...
Potato1
Potato9

它的作用是什么?

使用.contents标记子项作为列表提供。

>>> for tag in soup.find_all("td"):
...     print tag.contents
...
[u'Potato1 ', <span somestuff...="">Potato2</span>]
[u'Potato9 ', <span somestuff...="">Potato10</span>]

因为我们只对第一个元素感兴趣,所以我们选择

print tag.contents[0]

答案 1 :(得分:1)

另一种方法,与tag.contents[0]不同,它保证文本是一个 NavigableString而不是来自子Tag内的文字的内容是:

[child for tag in soup.find_all("td") 
 for child in tag if isinstance(child, bs.NavigableString)]

这是一个突出差异的例子:

import bs4 as bs

content = '''
<td>Potato1 <span>Potato2</span></td>
<td><span>FOO</span></td>
<td><span>Potato10</span>Potato9</td>
'''
soup = bs.BeautifulSoup(content)

print([tag.contents[0] for tag in soup.find_all("td")])
# [u'Potato1 ', <span>FOO</span>, <span>Potato10</span>]

print([child for tag in soup.find_all("td") 
       for child in tag if isinstance(child, bs.NavigableString)])
# [u'Potato1 ', u'Potato9']

或者,使用lxml,您可以使用XPath td/text()

import lxml.html as LH

content = '''
<td>Potato1 <span>Potato2</span></td>
<td><span>FOO</span></td>
<td><span>Potato10</span>Potato9</td>
'''
root = LH.fromstring(content)

print(root.xpath('td/text()'))

产量

['Potato1 ', 'Potato9']