开发者

How can I get an XML element's attribute with Perl's XML::Simple?

I have a Perl script that reads a XML file that doesn't have content, only attributes in the element.

Like this:

<league>
<game name="bla"/>
</league>

Now I try to get the game attribute 'name'.

I tried using $xml->{league}->{开发者_如何转开发game}->{name} and $xml->{league}->{game}->['name'] but they are both not working. Something about a hash problem.

Is there anybody who can help me get the value?


Well, from the XML you posted, I get this:

Entity: line 3: parser error : Opening and ending tag mismatch: league line 0 and leage

It doesn't even appear to be a strict/warnings issue because it appears when I comment my USUW out.

But if you have the right tags, this should work:

$xml->{game}{name};

And if I call XMLin with KeepRoot => 1, you'll find it at:

    $xml->{league}{game}{name};

If you are having trouble locating how the data is being read in, do this:

use 5.010;
use strict;
use warnings;
use Data::Dumper;
use XML::Simple;

my $xml = XMLin( $input );
say Data::Dumper->Dump( [ $xml ], [ '$xml' ] );

And then use the path to the structures presented.


Note:

$xml->{league}->{game}->['name'];

should have died with: "Not an ARRAY reference at" even without warnings enabled. ['string'] is a reference to an array with the string 'string' as the sole element. And, if $xml->{league}{game} were an array, it would have died with a non-numeric error, because strings don't address arrays.


I normally instantiate my XML::Simple objects like this:

use XML::Simple ':strict';
my $xs = XML::Simple->new( KeepRoot => 1, KeyAttr => 1, ForceArray => 1 );

it allows the structure to be consistent between single and possibly multiple sub-elements. With those settings, this code gets your value:

#!/usr/bin/perl
use strict;
use warnings;
use XML::Simple ':strict';

my $xs = XML::Simple->new( KeepRoot => 1, KeyAttr => 1, ForceArray => 1 );
my $ref = $xs->XMLin('data.xml');
print $ref->{league}[0]{game}[0]{name};

I added another game tag, and an attribute on the league tag as an example, this is the xml:

<league name="baz"> 
    <game name="bla"/>
    <game name="foo"/>
</league>

And the Data::Dumper output is:

$VAR1 = {
          'league' => [
                      {
                        'game' => [
                                  {
                                    'name' => 'bla'
                                  },
                                  {
                                    'name' => 'foo'
                                  }
                                ],
                        'name' => 'baz'
                      }
                    ]
        };
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜