为什么我要将XPathContext与Perl的XML :: LibXML一起使用?

时间:2010-04-20 07:36:09

标签: xml perl

此脚本可以使用XPathContext,也可以不使用XPathContext。我为什么要将它与#!/usr/bin/env perl use warnings; use strict; use XML::LibXML; use 5.012; my $parser = XML::LibXML->new; my $doc = $parser->parse_string(<<EOT); <?xml version="1.0"?> <xml> Text im Dokument <element id="myID" name="myname" style="old" /> <object objid="001" objname="Object1" /> <element id="002" name="myname" /> </xml> EOT #/ # without XPathContext my $nodes = $doc->findnodes( '/xml/element[@id=002]' ); # with XPathContext #my $root = $doc->documentElement; #my $xc = XML::LibXML::XPathContext->new( $root ); #my $nodes = $xc->findnodes( '/xml/element[@id=002]' ); for my $node ( $nodes->get_nodelist ) { say "Node: ", $node->nodeName; print "Attribute: "; print $_->getName, '=', $_->getValue, ' ' for $node->attributes; say ""; } 一起使用?

{{1}}

1 个答案:

答案 0 :(得分:11)

使用XPathContext元素的主要原因是名称空间。您的文档没有名称空间,因此XPathContexts不会向您的查询添加任何内容。现在,假设你实际上有以下xml

my $doc = $parser->parse_string(<<EOT);
<?xml version="1.0"?>
<xml xmlns="http://my.company.com/ns/nsone" 
    xmlns:ns2="http://your.company.com/nstwo">
    Text im Dokument
    <ns2:element id="myID" name="myname" style="old" />
    <object objid="001" objname="Object1" />
    <element id="002" name="myname" />
</xml>
EOT 

您需要定义一个XPathContext才能定义名称空间,以便您可以进行名称空间感知的XPath查询:

my $root = $doc->documentElement;
my $xc = XML::LibXML::XPathContext->new( $root );
$xc->registerNs("ns2", "http://your.company.com/nstwo");
$xc->registerNs("ns1", "http://my.company.com/nsone");
my $nodes = $xc->findnodes( '/ns1:xml/ns2:element[@id="myID"]' );

否则,您没有简单的方法来使用名称空间感知的XPath语句。