使用Perl访问XML DOM中的兄弟元素?

时间:2015-06-04 09:38:29

标签: xml perl

对于我的问题,我让用户输入字符串来搜索提供者,然后提供者以及一些选择计划信息出现在控制台中。但是,我无法找到如何打印选择提供商+所需的其他信息。

例如:

沃达丰|| 12个月|| 120GB

沃达丰|| 24个月|| 200GB

我已经开始了,并且不要过多关注sting输入,因为我可以稍后解释,但我找不到如何首先搜索选择提供程序然后打印信息。每个提供者和所有信息都在<计划>节点(参见下面的XML)。

XML文件

<plans>
    <internet>
        <plan>
            <technology>ADSL2+</technology>
            <length>12</length>
            <provider>Vodafone</provider>
            <price>60</price>
            <mincost>600</mincost>
            <data>120</data>
            <shaping>128</shaping>
            <homebundle>true</homebundle>
        </plan>
        <plan>
            <technology>ADSL2+</technology>
            <length>12</length>
            <provider>Telstra</provider>
            <price>80</price>
            <mincost>800</mincost>
            <data>200</data>
            <shaping>256</shaping>
            <homebundle>true</homebundle>
        </plan> 
        (etc.)

当前的Perl文件

use XML::DOM;

my $dom_obj;
my $xml_file= shift;

my $parser = new XML::DOM::Parser;

die "Unable to parse XML document\n" unless $dom_obj = $parser->parsefile($xml_file);

my @nodes = $dom_obj->getElementsByTagName("plan"); #return list of objects of 'Plan'

foreach $elem (@nodes) #for each 'Plan' object
{
    foreach $child ($elem->getChildElements) #should return each element under plan?
    {
        print $child->getNodeValue; #should print elements
        print " ";
    }
    print "\n";
} 

我尝试了一个if语句,认为我很接近但只收到了错误。

foreach $elem (@nodes)
{
    if($elem->getElementByTagName("provider")->getFirstChild->getNodeValue =~ /Vodafone/){
        print "$unit->getElementByTagName("provider")->getFirstChild->getNodeValue";
        print " || ";
        print "$unit->getElementByTagName("length")->getFirstChild->getNodeValue";
        print " || ";

任何帮助将不胜感激:)

2 个答案:

答案 0 :(得分:2)

我对[{1}}不熟悉,所以倾向于选择XML::DOM。像这样:

XML::Twig

#!/usr/bin/perl use strict; use warnings; use XML::Twig; my $provider = 'Vodafone'; sub print_plan_summary { my ( $twig, $plan ) = @_; return unless $plan -> first_child_text('provider') eq $provider; print join ( "||", $plan -> first_child_text('provider'), $plan -> first_child_text('length')." months", $plan -> first_child_text('data'). " GB" ); } my $twig = XML::Twig -> new ( twig_handlers => { 'plan' => \&print_plan_summary } ) -> parsefile('yourXML.xml'); 允许您设置处理程序,它们接受xml的子集(在本例中为XML::Twig个元素)并单独处理它们。因为我们可以做到这一点,我们可以随意操作,或者只是“简单地”从中提取数据。

答案 1 :(得分:1)

如果你可以使用别的东西,XML::Simple就很容易了。通常我不喜欢XML :: Simple,但是使用这种直接的XML结构它确实有用。

只需将文件(我将其放在__DATA__部分中)读入数据结构,然后迭代计划。那些是在arrayref中。现在您需要做的就是加入hashref值。

use strict;
use warnings;
use feature 'say';
use XML::Simple;

my $xs   = XML::Simple->new;
my $data = $xs->XMLin( \*DATA );


foreach my $plan ( @{ $data->{internet}->{plan} } ) {
    next if $plan->{provider} ne 'Vodafone';
    say join q{ || }, $plan->{provider}, $plan->{length} . ' months', $plan->{data} . 'gb';
}