2016-04-05 6 views
1

Zuerst Entschuldigung für diese noob Frage, ich bin neu in XML-Parsing. Ich versuche, einige grundlegende XML mit xml::twig zu analysieren. Ich habe es geschafft, einige Elemente mit dem unten stehenden Perl-Skript zu extrahieren, aber ich habe einige Schwierigkeiten mit anderen.Parsing XML mit variierendem Format

Ich habe es geschafft, die itemId und title mit dem unten angegebenen Code zu extrahieren. Aus irgendeinem Grund extrahiert das Skript jedoch nicht die convertedCurrentPrice. Ich möchte, dass der Preis extrahiert wird - das wäre 74 im folgenden XML-Ausschnitt. Ich vermute, dass dies nicht funktioniert, weil die XML die Informationen für die convertedCurrentPrice in einem etwas anderen Format als die itemID und title anzeigt.

Wie kann ich mein Skript so ändern, dass die convertedCurrentPrice wie die anderen Werte extrahiert wird?

Hier ist ein Beispiel für die XML-Datei (testxml.xml).

<itemId>222bb5786411</itemId><title>Radiohead In Rainbows Box Set Vinyl Deluxe Limited Edition</title><sellingStatus><currentPrice currencyId="GBP">74.0</currentPrice><convertedCurrentPrice currencyId="GBP">74.0</convertedCurrentPrice> 

Hier ist mein Perl-Skript;

#!/bin/perl -w 

use strict; 
use XML::Twig; 

my $twig = XML::Twig->new(
twig_handlers => {item => \&acct} 
); 
$twig->parsefile("testxml.xml"); 

sub acct { 
my ($t, $elt) = @_; 

     for my $tag (qw(itemId title convertedCurrentPrice)) {   
       print $elt->field($tag), "\n"; 
        } 
         print "\n"; 
         print "\n"; 
         } 


__END__ 

Antwort

0

Zunächst einmal - um dies richtig zu beantworten, brauchen wir wirklich ein paar gültige XML. Deines ist nicht.

Ich denke, die Wurzel des Problems ist, dass Sie nicht wirklich convertedCurrentPrice aus item extrahieren können, weil es unter sellingStatus

verschachtelt ist Es ist schwer, jedoch sicher zu sein, weshalb wir gültige XML tun müssen, wirklich. Ich habe deine nach bestem Wissen rekonstruiert, und genau das habe ich entdeckt.

Führen Sie Ihre XML durch einen ziemlich Drucker:

XML::Twig -> new (pretty_print => 'indented_a') -> parsefile('testxml.xml') ->print; 

Sie könnten Sie erhalten finden so etwas wie:

<xml> 
    <item> 
    <itemId>222bb5786411</itemId> 
    <title>Radiohead In Rainbows Box Set Vinyl Deluxe Limited Edition</title> 
    <sellingStatus> 
     <currentPrice currencyId="GBP">74.0</currentPrice> 
     <convertedCurrentPrice currencyId="GBP">74.0</convertedCurrentPrice> 
    </sellingStatus> 
    </item> 
</xml> 

Ich würde auch vorschlagen - dies für einen Zweig Handler kein Job ist, es sei denn, es ist etwas anderes los, so würde ich es eher so angehen:

#!/usr/bin/env perl 
use strict; 
use warnings; 
use XML::Twig; 

my $twig = XML::Twig -> new() -> parse (\*DATA); 

foreach my $item ($twig -> findnodes ('//item')) { 
    print join ",",(map { $item -> get_xpath($_,0)->text } qw (itemId title sellingStatus/convertedCurrentPrice)), "\n"; 
} 


$twig -> set_pretty_print('indented_a'); 
$twig -> print; 

__DATA__ 
<xml><item><itemId>222bb5786411</itemId> 
<title>Radiohead In Rainbows Box Set Vinyl Deluxe Limited Edition</title> 
<sellingStatus><currentPrice currencyId="GBP">74.0</currentPrice> 
<convertedCurrentPrice currencyId="GBP">74.0</convertedCurrentPrice> 
</sellingStatus> 
</item></xml> 

Aber Sie könnten tun:

$item -> first_child('sellingStatus') -> field('convertedCurrentPrice') 

anstatt es über xpath Ausdrücke zu tun.