我有以下解析xml的方法
import re
from lxml.html.soupparser import fromstring
inString = """
<doc>
<q></q>
<p1>
<p2 dd="ert" ji="pp">
<p3>1</p3>
<p3>2</p3>
<p3>32</p3>
<p3>3</p3>
</p2>
<p2 dd="ert" ji="pp">
<p3>4</p3>
<p3>5</p3>
<p3>ABC</p3>
<p3>6</p3>
</p2>
</p1>
<r></r>
<p1>
<p2 dd="ert" ji="pp">
<p3>7</p3>
<p3>8</p3>
<p3>ABC</p3>
<p3>9</p3>
</p2>
<p2 dd="ert" ji="pp">
<p3>10</p3>
<p3>11</p3>
<p3>XYZ</p3>
<p3>12</p3>
</p2>
</p1>
</doc>
"""
root = fromstring(inString)
#nodes = root.xpath("./doc//p1/p2/p3[contains(text(),'ABC') or contains(text(),'XYZ')]/preceding-sibling::p3")
ns = {"re": "http://exslt.org/regular-expressions"}
nodes = root.xpath(".//p3[re:match(.,'XYZ') or re:match(.,'ABC')]/preceding-sibling::p3", namespaces=ns)
这让我
4 5 7 8 10 11
所以它完全跳过了第一个<p2>
我的理想输出是
1 2 32 3 4 5 7 8 10 11
所以,如果我在<p2>
中找不到<p3>ABC<p3>
或<p3>XYZ<p3>
,我仍然想要那<p3>
的所有<p2>
。有可能吗
编辑
我试过了
".//p3[re:match(.,'XYZ') or re:match(.,'ABC')]/preceding-sibling::p3 | .//p3"
但这让我
1 2 32 3 4 5 ABC 6 7 8 ABC 9 10 11 XYZ 12
这就是一切
部分解
我试了以下方法
".//p3[re:match(.,'XYZ') or re:match(.,'ABC')]/preceding-sibling::p3 | .//p3[not (contains(text(),'ABC') or contains(text(),'XYZ'))]/preceding-sibling::p3"
这让我
1 2 32 4 5 ABC 7 8 ABC 10 11 XYZ
这是更好的,但仍然是不正确的。请注意,它缺少6
,并且包含了我不想要的ABC
和XYZ
好的开始,那么:
也就是说:对于没有p3子级等于ABC或XYZ的p2,给我p3子级
(字符串等于而不是regexp,因为在本例中不需要regexp,但可以使用regexp)
相关问题 更多 >
编程相关推荐