当使用lxml.html解析html时,等同于InnerHTML

2024-04-24 08:13:38 发布

您现在位置:Python中文网/ 问答频道 /正文

我正在编写一个使用lxml.html解析网页的脚本。在我的时间里,我做了一些漂亮的工作,但是现在由于它的速度,我正在尝试使用lxml。

我想知道库中最明智的方法是做与Javascript的InnerHtml等价的事情,即检索或设置标记的完整内容。

<body>
<h1>A title</h1>
<p>Some text</p>
</body>

因此,InnerHtml是:

<h1>A title</h1>
<p>Some text</p>

我可以使用hacks(转换成string/regex等)来实现,但我假设有一种正确的方法可以使用由于不熟悉而丢失的库来实现。谢谢你的帮助。

编辑:感谢pobk如此快速有效地向我展示了这方面的方法。对任何人来说,这就是我的结局:

from lxml import html
from cStringIO import StringIO
t = html.parse(StringIO(
"""<body>
<h1>A title</h1>
<p>Some text</p>
Untagged text
<p>
Unclosed p tag
</body>"""))
root = t.getroot()
body = root.body
print (element.text or '') + ''.join([html.tostring(child) for child in body.iterdescendants()])

请注意,lxml.html解析器将修复未关闭的标记,因此如果这是一个问题,请小心。


Tags: 方法textfrom标记importchildtitlehtml
3条回答
import lxml.etree as ET

     body = t.xpath("//body");
     for tag in body:
         h = html.fromstring( ET.tostring(tag[0]) ).xpath("//h1");
         p = html.fromstring(  ET.tostring(tag[1]) ).xpath("//p");             
         htext = h[0].text_content();
         ptext = h[0].text_content();

您还可以使用.get('href')作为标记,使用.attrib作为属性

这里的标记no是硬编码的,但是您也可以动态地执行此操作

可以使用根节点的getchildren()或iterdescendants()方法获取ElementTree节点的子节点:

>>> from lxml import etree
>>> from cStringIO import StringIO
>>> t = etree.parse(StringIO("""<body>
... <h1>A title</h1>
... <p>Some text</p>
... </body>"""))
>>> root = t.getroot()
>>> for child in root.iterdescendants(),:
...  print etree.tostring(child)
...
<h1>A title</h1>

<p>Some text</p>

这可能会出现以下情况:

print ''.join([etree.tostring(child) for child in root.iterdescendants()])

很抱歉再次提出此问题,但我一直在寻找解决方案,而您的解决方案包含一个错误:

<body>This text is ignored
<h1>Title</h1><p>Some text</p></body>

将忽略根元素正下方的文本。我最后这样做了:

(body.text or '') +\
''.join([html.tostring(child) for child in body.iterchildren()])

相关问题 更多 >