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

I am reading an XML file in perl and looping through the items and manipulating data. If I have 2 or more 'menuitems' in my xml file it works ok. if i only have one like the code below I get "Not an ARRAY reference" at the while loop line - Please explain Also I changed the codeing to ForceARRAY to 1 $xmlconfig = XMLin($xml,ForceArray => 1); its works for single nodes and error goes off. Its not working for morethan one element.
while(my $batch_aid = $xmlconfig->{order}->{'item-info'}->{batch}->{'b +atch-member'}->{aid}){ my $batch_pii = $xmlconfig->{order}->{'item-info'}->{batch}->{'batch +-member'}->[$i]->{'pii'}; my $batch_pit = $xmlconfig->{order}->{'item-info'}->{batch}->{'batch +-member'}->[$i]->{'pit'}; my $batch_doi = $xmlconfig->{order}->{'item-info'}->{batch}->{'batch +-member'}->[$i]->{'doi'}; $orderin{$batch_aid} = { 'pit' => $batch_pit, 'pii' => $batch_pii, 'doi' => $batch_doi, }; my $Eextra=''; $i++; $orderin{subitem}='Yes'; }
and XML file like below
<?xml version="1.0" encoding="iso-8859-1"?> <?xml-stylesheet type="text/xsl" href="coversheet.xsl" ?> <!DOCTYPE orders SYSTEM "ptsiiiorder127.dtd"[]> <orders> <order> <time day="19" month="06" yr="2009" hr="11" min="21" sec="27" /> <po-number>T02793939</po-number> <due-date> <date day="06" month="07" yr="2009" /> </due-date> <prod-site>ESEO - Elsevier Journals</prod-site> <opco>OCUK - Operating Company Elsevier Ltd</opco> <stage step="S100" /> <executor type="TYPESETTER" addressee="yes"> <exec-code>TNQ</exec-code> <exec-name>TnQ Books and Journals Pvt Ltd</exec-name> <aff> <address>Baid Hi-Tech Park</address> <address-contd>Block No 38, East Coast Road</address-contd> <zipcode zipcode-pos="AFTERCTY">600 041</zipcode> <cty>Thiruvanmiyur, Chennai</cty> <cny>India</cny> <tel>+91-44-24426085,6,7</tel> <fax>+91-44-24426088</fax> </aff> <datasetid>TNQ000511948</datasetid> </executor> <executor type="WAREHOUSE" addressee="no"> <exec-code>NOWAR</exec-code> <exec-name>No warehouse</exec-name> <aff> <organization>Elsevier</organization> <cny>Netherlands</cny> </aff> </executor> <item-info> <version-no>S100.1</version-no> <jid>RMEDU</jid> <aid>131</aid> <pii>S1745-0454(09)00034-3</pii> <embargo-until-stage>S300</embargo-until-stage> <batch> <batch-member> <aid>131.1</aid> <pit>LIT</pit> <pii>S1745-0454(09)00035-5</pii> <doi>10.1016/j.rmedu.2009.06.003</doi> </batch-member> </batch> <item-title>Literature Reviews: Secondary Care</item-title> <editor>Dr. J. Hurst</editor> <prd-type-as-sent>FTP</prd-type-as-sent> <online-version type="print" /> <pit>BPH</pit> <copy-edit-content required="no" /> <no-mns-pages>2</no-mns-pages> <no-phys-figs>0</no-phys-figs> <no-bw-figs>0</no-bw-figs> <no-web-colour-figs>0</no-web-colour-figs> <no-colour-figs>0</no-colour-figs> <no-e-components>0</no-e-components> <righthand-start>N</righthand-start> <copyright-status>000</copyright-status> <first-author> <snm>No Author</snm> </first-author> <corr-author> <snm>No Author</snm> <aff> <organization>USE THIS AUTHOR FOR ARTICLES WITH NO AUTHOR!!! +</organization> <address>DO NOT OVERWRITE THIS AUTHOR !!!</address> <cty>DO NOT OVERWRITE THIS AUTHOR !!!</cty> </aff> </corr-author> <offprint-payment payment="no" /> </item-info> </order> </orders>

Replies are listed 'Best First'.
Re: XML::Simple question
by grantm (Parson) on Aug 02, 2009 at 03:03 UTC
    You need to use the ForceArray option. Read about it here.
Re: XML::Simple question
by jbt (Chaplain) on Aug 01, 2009 at 16:47 UTC
    Assuming $xmlconfig looks something like:

    my $xmlconfig = { 'order' => { 'item-info' => { 'batch' => { 'batch-member' => { 'aid' => {} } } } } };
    'batch-member' is hash reference, and not an array reference. Check the three lines after the while loop dereferencing $i:

    while(my $batch_aid = $xmlconfig->{order}->{'item-info'}->{batch}->{'b +atch-member'}->{aid}){ my $batch_pii = $xmlconfig->{order}->{'item-info'}->{batch}->{'batch +-member'}->{$i}->{'pii'}; my $batch_pit = $xmlconfig->{order}->{'item-info'}->{batch}->{'batch +-member'}->{$i}->{'pit'}; my $batch_doi = $xmlconfig->{order}->{'item-info'}->{batch}->{'batch +-member'}->{$i}->{'doi'}; $orderin{$batch_aid} = { 'pit' => $batch_pit, 'pii' => $batch_pii, 'doi' => $batch_doi, }; my $Eextra=''; $i++; $orderin{subitem}='Yes'; }
      Thanks Monks, I have solved by using Forcearray
      $xmlconfig = XMLin($xml,ForceArray => [qw{batch-member}]); my $count= (@{$xmlconfig->{order}->{'item-info'}->{batch}->{'batch-mem +ber'}}); #print $count; for ($i=0; $i<=$count; $i++ ){ my $batch_aid = $xmlconfig->{order}->{'item-info'}->{batch}->{'batch +-member'}->[$i]->{'aid'}; my $batch_pii = $xmlconfig->{order}->{'item-info'}->{batch}->{'batch +-member'}->[$i]->{'pii'}; my $batch_newpii=$batch_pii; $batch_newpii=~s/[^A-z0-9]//gi; my $batch_pit = $xmlconfig->{order}->{'item-info'}->{batch}->{'batch +-member'}->[$i]->{'pit'}; my $batch_doi = $xmlconfig->{order}->{'item-info'}->{batch}->{'batch +-member'}->[$i]->{'doi'}; $orderin{$batch_aid} = { 'pit' => $batch_pit, 'pii' => $batch_pii, 'doi' => $batch_doi, }; my $Eextra=''; $i++; $orderin{subitem}='Yes'; }
Re: XML::Simple question
by Jenda (Abbot) on Aug 03, 2009 at 13:18 UTC