lxml XPath-过滤所有文本,包括尾部

时间:2013-12-28 08:06:29

标签: python xpath lxml

我正在尝试使用lxml和Python从网站中过滤掉文本,但格式化可能非常不规则。 (这是一个论坛。)

例如,我可能有:

<a>
   <c>
      <d>
         MARKER some text
      </d>
   </c>
   MARKER other text 1
   <b>MARKER other text 2</b>
   M<b>ARKE</b>R <e>other</e> text 3
</a>

我希望我的xpath能够回复我:

MARKER other text 1
<b>MARKER other text 2</b>
M<b>ARKE</b>R <e>other</e> text 3

换句话说,我希望能够解析嵌套文本,但也会返回带有标记的文本。

我目前拥有的是:

filter = "//text()[not(parent::d[parent::c]) and contains(., 'MARKER')]"
filtered = root.xpath(self.vote_xpath)
for i in filtered:
    print(i)

其中root是从字符串解析的元素树,它返回我:

MARKER other text 1
MARKER other text 2

这使我无法使用MARKER返回最后一个文本,并且无法保留我想要的格式。

我该如何从这里开始?

编辑: 好的,我一直在使用xpath。

//node()[not(parent::d[parent::c]) and contains(., 'MARKER')]

运行:

<a>
   <c>
      <d>
         some text
      </d>
   </c>
   other text 1
   <b>other text 2</b>
   M<b>ARKE</b>R <e>other</e> text 3
</a> 

成功注册了由MARKER代码分解的<b>,因为node()将整个节点传递给contains过滤器。但是,它返回父节点整数的匹配,在这种情况下,它只返回整个<a>节点及其所有内容。

我应该如何继续使xpath只返回匹配的部分?

1 个答案:

答案 0 :(得分:2)

从不同的角度看待它可能会有所帮助。您的半完整解决方案专注于所需数据的父元素,但您也可以使用子路径标识符或相对路径标识符。

我得到了这个XPATH:

a/c/following-sibling::node()

要返回:

   MARKER other text 1

<b>MARKER other text 2</b>


   M
<b>ARKE</b>

R 
<e>other</e>

 text 3

虽然这不是您正在寻找的格式,但它是正确的数据,XPATH并不是真正用于格式化您的结果,所以没有太多可以在那里工作。