SyntaxError:使用 lxml iterfind 的谓词无效

SyntaxError: invalid predicate using lxml iterfind

提问人:thetruth 提问时间:12/21/2022 最后编辑:thetruth 更新时间:12/22/2022 访问量:154

问:

我目前正在努力迭代 XPath 表达式。我正在尝试检索包含“[[SOMETHING|”子字符串的所有系统输出节点。问题是我收到以下指向 tree.iterfind 的语法错误。

    for elem in tree.iterfind('.//system-out[contains(.,"[[SOMETHING|")]'):
                ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "src/lxml/etree.pyx", line 2288, in lxml.etree._ElementTree.iterfind
  File "src/lxml/etree.pyx", line 1588, in lxml.etree._Element.iterfind
  File "src/lxml/_elementpath.py", line 312, in lxml._elementpath.iterfind
  File "src/lxml/_elementpath.py", line 295, in lxml._elementpath._build_path_iterator
  File "src/lxml/_elementpath.py", line 237, in lxml._elementpath.prepare_predicate
SyntaxError: invalid predicate
tree = etree.parse(test_file)
for elem in tree.iterfind('.//system-out[contains(.,"[[SOMETHING|")]'):
     print("do something")

以上是我的代码。据我所知,我没有任何语法错误。我还尝试使用免费的格式化程序工具测试 xpath 表达式,这似乎有效。 我似乎看不出哪里出了问题。我尝试使用 lxml 提供的“findall”函数,但收到相同的错误。我还尝试使用 etree 编译 xpath 表达式。XPath 函数转换为属性,但是我收到了一个 TypeError,上面写着以下内容,这是有道理的。

TypeError: 'lxml.etree.XPath' object is unsliceable

我错过了什么吗?还是只是 lxml 包本身不支持的表达式?

python xml xpath xml 解析 lxml

评论

0赞 Barmar 12/21/2022
它抱怨 XPath 表达式无效。
0赞 thetruth 12/21/2022
@Barmar 但是使用此工具似乎可以工作: 链接 lxml 是否期望某种不同的格式?
1赞 Martin Honnen 12/21/2022
ElementTree 和 lxml 中的方法 (, , , 'findtext') 都不支持完整的 XPath 1.0 语法,因此该错误可能只是表明您传入的表达式过于复杂而无法用作“元素路径”,即使它是合法的 XPath 1.0 表达式也是如此。finditerfindfindfindall
1赞 Martin Honnen 12/21/2022
docs.python.org/3/library/......列出了支持的功能,对谓词中的 XPath 函数(如 )的调用根本没有列出。contains

答:

0赞 Prophet 12/21/2022 #1

如果不能使用,而不是仍然可以使用并且足够独特,我建议不要使用这个:SOMETHING[[SOMETHING|.//system-out[contains(.,"[[SOMETHING|")]

'.//system-out[contains(.,"SOMETHING")]'

所以整个代码行将是

for elem in tree.iterfind('.//system-out[contains(.,"SOMETHING")]'):

评论

0赞 thetruth 12/21/2022
这仍然会引发语法错误:无效谓词:for elem in tree.iterfind('.//system-out[contains(.,"SOMETHING")]'):
0赞 Prophet 12/21/2022
好吧,也许这是因为您使用的方法不支持 Martin Honnen 提到的复杂方法
0赞 thetruth 12/22/2022 #2

正如 Martin Honnen 在评论中解释的那样,ElementTree 和 lxml 中的方法 (, , ) 不支持解释错误的完整 XPath 1.0 语法。finditerfindfindfindallSyntaxError: invalid predicate

我使用了这个函数,它确实支持 XPath 1.0 语法。为了能够检索 XML 文件中的文本,我随后使用函数的结果,通过使用可以理解的更简单的 XPath 表达式来迭代所有匹配项。lxml.etree.xpath()xpath()iterfind

occ = tree.xpath('.//system-out[contains(.,"[[SOMETHING|")]')[0].text
for elem in tree.iterfind(f'.//*[.="{occ}"]'):
     print("do something")