首页 > 解决方案 > 当有一些相同的标签名称时,如何使用 perl 脚本过滤 xml 标签?

问题描述

我正在使用命令行进行过滤,下面是我的 XML 文件

<data>
    <numbers>
        <value>1</value>
        <extra>
            <value>a</value>
        </extra>
    </numbers>
    <numbers>
        <value>2</value>
        <extra>
            <value>b</value>
        </extra>
    </numbers>
    <numbers>
        <value>3</value>
    </numbers>
    <numbers>
        <value>10</value>
        <extra>
            <value>c</value>
        </extra>
    </numbers>
    <numbers>...</numbers>
    ...
</data>

如您所见,我想要“数字”下的“值”标签中的值,但是当我使用我的perl代码过滤它时,“额外”标签下的“值”也会出现,我应该怎么做保留“数字”下的“价值”标签并删除“额外”下的“价值”标签???

下面是我的 perl 代码:(命令行格式)

perl -nle 'while(<stdin>){if(/data|numbers|value/){chop; print}}' < sample.xml > output.xml

此命令行的输出是:

<data>
    <numbers>
        <value>1</value>
            <value>a</value>
    </numbers>
    <numbers>
        <value>2</value>
            <value>b</value>
    </numbers>
    <numbers>
        <value>3</value>
    </numbers>
    <numbers>
        <value>10</value>
            <value>c</value>
    </numbers>
    <numbers>...</numbers>
    ...
</data>

是的,“extra”标签被删除了,但是“extra”标签中的“value”标签还在,我不要了,请帮我编辑我的命令行代码,非常感谢!!!

标签: xmlperl

解决方案


当已经存在优秀的 XML 解析器时,花费大量时间和精力编写自己的 XML 解析器是没有意义的。


黑名单方法

要删除extra元素:

use XML::LibXML qw( );

my $doc = XML::LibXML->new->parse_file('sample.xml');

for my $node ($doc->findnodes('/data/numbers/extra')) {
   $node->unbindNode();
}

$doc->toFile('output.xml');

白名单方法

要删除除您说要保留的元素之外的所有元素:

use XML::LibXML qw( );

sub qualified_name {
   my ($node) = @_;
   if (defined($node->namespaceURI())) {
      return sprintf("{%s}%s", $node->namespaceURI(), $node->nodeName());
   } else  {
      return $node->nodeName();
   }
}

my $doc = XML::LibXML->new->parse_file('sample.xml');

for my $node ($doc->findnodes('/data/*')) {
   if (qualified_name($node) ne "numbers") {
      $node->unbindNode();
      next;
   }

   for my $node ($node->findnodes('*')) {
      if (qualified_name($node) ne "value") {
         $node->unbindNode();
         next;
      }
   }
}

$doc->toFile('output.xml');

推荐阅读