ralibm has asked for the wisdom of the Perl Monks concerning the following question:

I can dereference a tree into single level struct. But when I try and do the same with a multi level struct like below all the subFields are undef and then there is a new empty hash inserted into the tree.

Any ideas as to why my derefrencing is being treated like some kind of setter instead of a getter.

$self is a hash ref of Field passed in by argument.
struckt subField => { subField1 => '$', subField2 => '$', subField3 => '$', subField4 => '$', }; struck Field => { field1 => 'subField', field2 => 'subField', }; my @list (field1, field2); my @subList (subField1, subField2, subField3, subField4); if ($res->is_success) { my $tree = $s->XMLin($res->content); foreach $item (@list) { foreach $subItem (@subList) { $self->$item->$subItem ( $tree->{level1}->{level2}->{$item}->{su +bItem} ); } } } else { print "GET request failed: $getURL\n"; }

Replies are listed 'Best First'.
Re: Need Help Understanding Parsing XML into multi level struck
by davido (Cardinal) on Mar 17, 2004 at 22:54 UTC
    my @list (field1, field2); my @subList (subField1, subField2, subField3, subField4);

    What are those lines doing? For me they don't even compile. Is this some pseudocode notation I should be privy to?


    Dave

      Yes this is pseudo code. The data stream that feeds the tree is proprietary.

      The lines you've highlighted are used to control the outer and inner loops. The list elements are also used to identify the nodes in the structs.

      So basically it will look something like this:

      self => Field1 => { subField1 => 'thingy1' subField2 => 'thingy2' subField3 => 'thingy3' subField4 => 'thingy4' } Field2 => { subField1 => 'thingy1' subField2 => 'thingy2' subField3 => 'thingy3' subField4 => 'thingy4' } }
      I can get this to work when I don't have subfields, but the XML is more granular for the module I'm now building.
        When you use the Data::Dumper module, does your overall structure look like you think it should? For example, do you get the expected output when you say:
        print Dumper $tree;

        Dave

Re: Need Help Understanding Parsing XML into multi level struck
by TomDLux (Vicar) on Mar 18, 2004 at 00:10 UTC

    While you're fixing up spelling mistakes, "struckt subField"? "struck Field"?

    Have you considered verifying whether $tree->{level1}->{level2}->{$item} and $tree->{level1}->{level2}->{$item}->{subItem} exist, before accessing them?

    If $self is a reference to a hash, what is $self->$item, $self->$item->$subItem? A subroutine, I guess, since it's invoked and passed $tree->{level1}->{level2}->{$item}->{subItem}.

    --
    TTTATCGGTCGTTATATAGATGTTTGCA

      Definetly dumped the $tree once I started having problems.

      I'm also using 'use strict', so spelling isn't an issue with the code.

      I copied/pasted the tree output into the source in case I had mis-spelled a field name or list item.

      I've exashed my O'Reilly cookbook for every example that I could canibalize, plus what I could find off CPAN examples.

      I've scrubed the code and I can send it to you to pour over. It's not very big, just over 100 lines, mostly for clarity.
        Sorry I didn't awnser the other half of your question.

        $self is a ref to the Field structure. $self->$item is a ref to one of the keys in Field, dependant on the looping. $self->$item->$subItem is a ref to one of the keys in SubField for Field, again depending on the iteration of the loops.

        This is a ref to the value in the tree at $subItem for $item for Level2 for Level1.

        $tree->{Level1}->{Level2}->{$item}->{$subItem}

        This is supose to act as a setter for $self. $self->$item->$subItem ( ) ;

        Simply put, you get $subItem from tree and place it into $subItem of $self.
Re: Need Help Understanding Parsing XML into multi level struck
by Anonymous Monk on Mar 19, 2004 at 02:05 UTC
    Im somewhat puzzled by your code, particularly as it relates to your Question (as posed in the title)

    My 1 line answer to anything XML is use XML::Simple

    Heres why: you probably have some xml files lying around, these provide good fodder for parsing into data structures, you can DataDump these and see what happens! By simply redirecting the output to a file, you can then go backwards.

    Theres a very good chance that XML::Simple will be the only tool you need. If not, it will get you a long way b4 you run out of gas.

    to get you started

    #!/usr/local/bin/perl -w
    
    use XML::Simple;
    use Data::Dumper;
    $Data::Dumper::Indent=1;
    use Getopt::Std;
    
    getopts('w') or die "bad args";
    foreach $file (@ARGV) {
        if ($file =~ /.xml$/) {
    	$data = XMLin($file, suppressempty=>1);
    	if ($opt_w) {
    	    $file =~ s|.*/(.*)\.xml|$1|;
    	    open (STDOUT, "> $file.pm");
    	}
    	print "# xml as data\n", Dumper $data;
        }
        else {
    	$data = do $file;
    	# print "data: ", Dumper $data;
    	if ($opt_w) {
    	    $file =~ s|.*/(.*)\.xml|$1|;
    	    open (STDOUT, "> $file.xml");
    	}
    	print "\n", XMLout($data);
        }
    }
    
Re: Need Help Understanding Parsing XML into multi level struck
by drfrog (Deacon) on Mar 19, 2004 at 19:11 UTC
    here is something that helped me, i found it on another PM thread but cant find link
    use XML::Simple; my $xs = XML::Simple->new( ForceArray => 1,suppressempty => '' ); my @href = $xs->XMLin(shift); print Dumper(@href);
    here is another way
    Parsing XML
      Or simpler
      use XML::Simple; my @href = XMLin(shift, ForceArray => 1, suppressempty => '' ); print Dumper @href;
      and then as a oneliner
      perl -MXML::Simple -e'print Dumper XMLin(shift, ForceArray => 1, suppr +essempty => "" )' foo.xml

      Makeshifts last the longest.