【发布时间】:2013-07-06 00:16:50
【问题描述】:
如何获取 XML 文档的所有文本内容,作为单个字符串 - like this Ruby/hpricot example,但使用 Python。
我想用一个空格替换 XML 标记。
【问题讨论】:
-
您接受的答案是错误的,如评论中所述。你会不接受它,以免错误的答案被固定在页面顶部吗?
如何获取 XML 文档的所有文本内容,作为单个字符串 - like this Ruby/hpricot example,但使用 Python。
我想用一个空格替换 XML 标记。
【问题讨论】:
使用标准库xml.etree
import xml.etree.ElementTree as ET
tree = ET.parse('sample.xml')
print(ET.tostring(tree.getroot(), encoding='utf-8', method='text'))
【讨论】:
我真的很喜欢 BeautifulSoup,如果可以避免的话,我宁愿不在 HTML 上使用正则表达式。
改编自:[this StackOverflow Answer]、[BeautifulSoup documentation]
from bs4 import BeautifulSoup
soup = BeautifulSoup(txt) # txt is simply the a string with your XML file
pageText = soup.findAll(text=True)
print ' '.join(pageText)
当然,您可以(并且应该)使用 BeautifulSoup 浏览页面以找到您要查找的内容。
【讨论】:
一个不需要像 BeautifulSoup 这样的外部库的解决方案,使用内置的 sax 解析框架:
from xml import sax
class MyHandler(sax.handler.ContentHandler):
def parse(self, filename):
self.text = []
sax.parse(filename, self)
return ''.join(self.text)
def characters(self, data):
self.text.append(data)
result = MyHandler().parse("yourfile.xml")
如果您需要文本中的所有空格保持不变,还可以在处理程序类中定义 ignorableWhitespace 方法,方法与定义 characters 的方式相同。
【讨论】:
这个问题实际上是an example in the lxml tutorial,它建议使用以下 XPath 表达式之一从文档中获取所有文本内容位作为字符串列表:
root.xpath("string()")root.xpath("//text()")然后,您需要将这些文本位组合成一个大字符串,str.join 可能使用str.strip 来消除每个位的前导和尾随空格,并忽略完全由空格组成的位:
>>> from lxml import etree
>>> root = etree.fromstring("""
... <node>
... some text
... <inner_node someattr="someval"> </inner_node>
... <inner_node>
... foo bar
... </inner_node>
... yet more text
... <inner_node />
... even more text
... </node>
... """)
>>> bits_of_text = root.xpath('//text()')
>>> print(bits_of_text) # Note that some bits are whitespace-only
['\n some text\n ', ' ', '\n ', '\n foo bar\n ', '\n yet more text\n ', '\n even more text\n']
>>> joined_text = ' '.join(
... bit.strip() for bit in bits_of_text
... if bit.strip() != ''
... )
>>> print(joined_text)
some text foo bar yet more text even more text
顺便说一句,如果你不想在文本位之间插入空格,你可以这样做
etree.tostring(root, method='text', encoding='unicode')
如果你处理的是 HTML 而不是 XML,并且使用 lxml.html 来解析你的 HTML,你可以调用 .text_content() 的方法您的根节点以获取它包含的所有文本(尽管同样不会插入空格):
>>> import lxml.html
>>> root = lxml.html.document_fromstring('<p>stuff<p>more <br><b>stuff</b>bla')
>>> root.text_content()
'stuffmore stuffbla'
【讨论】:
编辑:这是一个在我认为一个空格缩进是正常的时候发布的答案,正如 cmets 提到的那样,这不是一个 好 的答案。查看其他一些更好的解决方案。仅出于存档原因将其留在这里,请勿不要关注它!
你要求 lxml:
reslist = list(root.iter())
result = ' '.join([element.text for element in reslist])
或者:
result = ''
for element in root.iter():
result += element.text + ' '
result = result[:-1] # Remove trailing space
【讨论】:
<node>text <subnode>x</subnode>text2</node> 失败
text而忽略tail会发生什么:stackoverflow.com/q/12412264/407651