2017-11-15 14 views
1

私は以下のXMLを持っています。XpathはXML :: Twig :: XPath :: Eltと連携していません

<Path> 
    <To> 
    <My> 
     <Node key="11"> 
     <ChildA>1A</ChildA> 
     <ChildB key="Key1">1B</ChildB> 
     <ChildC> 
      <ChildD>ValD</ChildD> 
     </ChildC> 
     </Node> 
     <Node key="22"> 
     <ChildA>2A</ChildA> 
     <ChildB key="Key2">2B</ChildB> 
     <ChildC> 
      <ChildD>ValD</ChildD> 
     </ChildC> 
     </Node> 
    </My> 
    </To> 
</Path> 

そして、このXMLをXML :: Twig :: XPathを使用して解析しようとしています。 これは、XPath構文を使用して解析し、そこから要素を抽出するコードです。

use 5.010; 
use strict; 
use warnings FATAL => 'all'; 
use XML::Twig::XPath; #Issue with this shit as this thing was up to data but XML::XPath was not installed. So I did cpanm XML::XPath 
use XML::Twig; 
use Data::Dumper; 
my @xml; 

$xml[0] = q|<Path> 
    <To> 
    <My> 
     <Node key="11"> 
     <ChildA>1A</ChildA> 
     <ChildB key="Key1">1B</ChildB> 
     <ChildC> 
      <ChildD>ValD</ChildD> 
     </ChildC> 
     </Node> 
     <Node key="22"> 
     <ChildA>2A</ChildA> 
     <ChildB key="Key2">2B</ChildB> 
     <ChildC> 
      <ChildD>ValD</ChildD> 
     </ChildC> 
     </Node> 
    </My> 
    </To> 
</Path>|; 

my $twig = XML::Twig::XPath->new(pretty_print => 'indented')->parse($xml[0]); 

#Finding the whole Node, using xpath. This shit also works if you have Twig, not XPath. 
my @constraint = $twig->findnodes('/Path/To/My/Node[@key="22"]'); 
say $constraint[0]->sprint; 
say ref($constraint[0]); 

my $child_key = $constraint[0]->find('//ChildB/@key'); 
say $child_key; 

$ constraint [0]は正当にXMLノードを出力します。

そしておそらく間違っている私は$ child_keyがキー2ことを期待するが、それはKey1Key2

は私が何ができるかであることが判明しますか?完全なXPath検索を行うと、出力が得られます。

答えて

4

//ChildB/@key xpath式は、ルート要素から始まり、要素ChildBと属性@keyの任意の要素を探します。

あなたの枝$constraint[0]ではなく、が完全にツリーから取り除かれているのは混乱しています。これは完全なドキュメントツリーの一部のビューのようなものなので、//は実際には完全なツリーを表示します。文書のルートから始まり、<Node key="22">要素ではなく始まります。

.を使用して現在の要素を開始するように、findに連絡する必要があります。

#          V 
my $child_key = $constraint[0]->find('.//ChildB/@key'); 

今、あなたの出力のみ

Key2 
です
関連する問題