数组的perl数组,缺少元素

perl arrays of array, elements are missing

我正在尝试从 xml 字符串生成嵌套树结构的数组。

但是当我生成引用变量时 $output B1 中的一些元素丢失了(C1、D1、D2)。 $test使用XML::LibXML::Readercpan模块生成。

use strict;
use warnings;
use Data::Dumper;
use v5.10;

my $test = "start, /root/class1, A1
start, /root/class1/class2, B1
start, /root/class1/class2/class3, C1
start, /root/class1/class2/class3/class4, D1
end, /root/class1/class2/class3/class4, D1
start, /root/class1/class2/class3/class4, D2
end, /root/class1/class2/class3/class4, D2
end, /root/class1/class2/class3, C1
end, /root/class1/class2, B1
start, /root/class1/class2, B2
start, /root/class1/class2/class3, C2
start, /root/class1/class2/class3/class4, D1
end, /root/class1/class2/class3/class4, D1
start, /root/class1/class2/class3/class4, D2
end, /root/class1/class2/class3/class4, D2
start, /root/class1/class2/class3/class4, D3
end, /root/class1/class2/class3/class4, D3
end, /root/class1/class2/class3, C2
end, /root/class1/class2, B2
end, /root/class1, A1";

our $x = 0;

my $output = generator($test); 

say "Output: ". Dumper $output;

sub generator{
    my ($classes, $x, $subout) = (shift, shift, '');
    my @out;

    $x += 1;

    while($classes =~ /(start(.+?class$x\,\ (\w+))\n(.*?)end)/gsi){
        my ($data1, $value, $rest) = (, , );
        $subout = generator($rest,$x) if $rest;
        push @out, $value;

    }
    push @out, $subout if $subout;
#   say "X: $x ". Dumper \@out;
    return \@out;
}

输出为:

Output: $VAR1 = [
          'A1',
          [
            'B1',
            'B2',
            [
              'C2',
              [
                'D1',
                'D2',
                'D3'
              ]
            ]
          ]
        ];

我错过了什么吗? 任何其他创建数据结构的方法也有帮助。

xml:

<?xml version="1.0" encoding="UTF-8"?>
<root>
<class1 name="A1">
 <class2 name="B1">
  <class3 name="C1">
   <class4 name="D1">
   </class4>
   <class4 name="D2">
   </class4>
  </class3>
 </class2>
<class2 name="B2">
 <class3 name="C2">
  <class4 name="D1">
  </class4>
  <class4 name="D2">
  </class4>
  <class4 name="D3">
  </class4>
 </class3>
</class2>
</class1>
</root>

此代码将按照您的要求执行。但这基本上就是可怕的 XML::Simple 试图做的事情。它会丢失信息,一般 XML 文档

不可能
use strict;
use warnings 'all';

use XML::LibXML::Reader;

use constant XML_FILE => 'root.xml';

my %data;
my @stack = (\%data);

my $reader = XML::LibXML::Reader->new(location => XML_FILE);

while ( $reader->read ) {

    my $type = $reader->nodeType;

    if ( $type == XML_READER_TYPE_ELEMENT ) {
        next unless my $name = $reader->getAttribute('name');
        push @stack, ($stack[-1]{$name} = {});
    }
    elsif ( $type == XML_READER_TYPE_END_ELEMENT ) {
        pop @stack if $reader->getAttribute('name');
    }
}

use Data::Dump;
dd \%data;

输出

{
  A1 => {
          B1 => { C1 => { D1 => {}, D2 => {} } },
          B2 => { C2 => { D1 => {}, D2 => {}, D3 => {} } },
        },
}