BeautifulSoup中的.string和.text的区别
我在使用BeautifulSoup时发现了一些奇怪的情况,但找不到相关的文档来支持我的发现,所以我想在这里问问。
假设我们用BeautifulSoup解析了一些像这样的标签:
<td>Some Table Data</td>
<td></td>
官方推荐的提取数据的方法是用soup.string
。不过,这个方法在第二个<td>
标签上提取出来的是一个NoneType,也就是没有值。所以我试了试soup.text
(反正也没什么坏处),结果提取到了一个空字符串,正是我想要的。
但是我在文档中找不到任何关于这个的说明,我有点担心这样做是否合适,会不会在后面造成问题?
顺便说一下,我是在从网页上抓取表格数据,打算把这些数据做成CSV文件,所以我确实需要空字符串,而不是NoneType。
3 个回答
这个元素
<td></td>
并不包含一个空字符串。它的意思和下面这个是一样的
<td/>
这个没有任何子元素。对于XML来说,“没有文本”和“长度为零的文本”是一样的。
所以 soup.string
返回 NoneType
是正确的。
另外,可以参考这个链接:如何在Java中创建一个值为空字符串的XML文本节点
如果一个标签里面包含了多个内容,那么就不太清楚.string应该指向哪个内容,所以.string的定义是None,也就是没有值。
举个例子:
<td>sometext<p>sometext</p></td>
上面的代码如果执行td.string,会返回NoneType,因为td里面有文本和另一个p标签。但是如果执行td.text,就会得到:sometextsometext。
.string
在一个 Tag
类型的对象上会返回一个 NavigableString
类型的对象。而 .text
则会获取所有子字符串,并用指定的分隔符把它们连接起来。.text
的返回类型是 unicode
对象。
根据 文档,NavigableString
就像是 Python 的 Unicode
字符串,不过它还支持一些在 遍历树 和 搜索树 中描述的功能。
根据 关于 .string
的文档,如果 HTML 是这样的,
<td>Some Table Data</td>
<td></td>
那么在第二个 td
上使用 .string
会返回 None
。但是 .text
会返回一个空字符串,这个空字符串是一个 unicode
类型的对象。
为了更方便,
string
- 这是一个
tag
的便利属性,用来获取这个标签内的单个字符串。 - 如果
tag
只有一个字符串子元素,那么返回的就是这个字符串。 - 如果
tag
没有子元素或者有多个子元素,那么返回的就是None
。 - 如果这个
tag
有一个子标签,那么返回值是这个子标签的 'string' 属性,递归进行。
而 text
- 获取所有子字符串,并用指定的分隔符连接起来返回。
如果 HTML 是这样的:
<td>some text</td>
<td></td>
<td><p>more text</p></td>
<td>even <p>more text</p></td>
在四个 td
上使用 .string
会返回,
some text
None
more text
None
而 .text
会给出这样的结果,
some text
more text
even more text