【问题标题】:XML XPath 1.0 - How to correctly use 'not' function in XPath expressionXML XPath 1.0 - 如何在 XPath 表达式中正确使用“not”函数
【发布时间】:2014-03-13 05:28:51
【问题描述】:

我只想返回不包含 BB 子节点的 AA 节点。我正在使用 XPath 1.0 顺便说一句。

示例 xml 文件:

<?xml version="1.0" encoding="UTF-8"?>
<T>
 <AA>
  <ZZ>z</ZZ>        
 </AA>
 <AA>
  <BB>b1</BB>        
 </AA>
 <AA>
  <BB>b2</BB>        
  <CC>c</CC>        
 </AA>
 <AA>
  <CC>c</CC>        
  <DD>d</DD>        
 </AA>
</T>

所以对于上面的例子,只有第一个和最后一个 AA 节点应该被返回。 我尝试过类似的方法:

//AA/*[非(BB)]/..

...但这仍然返回所有 4 个 AA 节点。

'not' 功能在 1.0 中可用吗? 如果是这样,我做错了什么?谢谢...

【问题讨论】:

  • 不确定这与 Perl 有什么关系?
  • 抱歉,出于习惯……只有当我只包含一个“我的”stmt 时,嗯?

标签: xml perl xpath


【解决方案1】:

请记住

//AA/*[not(BB)]/..

只是一种简单的方式或写作

descendant::AA/child::*[not(child::BB)]/parent::node()

这样更明显,BB 不会检查上下文节点的名称是否为 BB,它会查找名为 BB 的子节点。


您正在检查AA 的子元素是否有子元素BB。

您想检查AA 元素是否有子元素BB。

//AA[not(BB)]

【讨论】:

  • 谢谢;是的,这行得通……我可以发誓我试过了……天哪!
【解决方案2】:

您的表达式会选择属于 AA 的子节点的节点,这些节点没有 BB 作为子节点。如果你对AA 节点做出断言,那么你应该得到你想要的:

use strict;
use warnings;

use XML::XPath;

my $xp = XML::XPath->new( filename => 'test.xml');

my $nodeset = $xp->find('//AA[not(BB)]');

foreach my $node ($nodeset->get_nodelist) {
  print "FOUND:\n";
  print ' ', $node->toString, "\n";
}

哪些输出:

FOUND:
 <AA>
  <ZZ>z</ZZ>        
 </AA>
FOUND:
 <AA>
  <CC>c</CC>        
  <DD>d</DD>        
 </AA>

【讨论】:

    【解决方案3】:

    你可以使用:

    //AA[not(BB)]
    

    您尝试的表达式选择了 AA 中不包含 BB 的元素。

    【讨论】:

      猜你喜欢
      • 2018-10-25
      • 2022-01-16
      • 2014-02-19
      • 1970-01-01
      • 1970-01-01
      • 2014-11-16
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多