有没有办法让XML :: Twig理解UTF-16编码的XML文件?

时间:2015-01-22 23:45:59

标签: xml perl xml-twig

有没有办法让XML::Twig理解UTF-16编码的XML文件?

阅读文件的代码是教程中所述:

use warnings;
use strict;

use XML::Twig;

# ...

my $twig=XML::Twig->new(
  twig_handlers => { ... },
  prety_print => 'indented',
  keep_encoding => 1,
};

# ...

$twig->parsefile('myXmlFile.xml');  # <= line 71

错误是:

error parsing tag '<RIBBON>' at /usr/lib/perl5/vendor_perl/5.14/x86_64-cygwin-threads/XML/Parser/Expat.pm line 470
 at ../../cv32/res/convert-xml-string2.pl line 71
 at ../../cv32/res/convert-xml-string2.pl line 71

XML就像这样开始:

<?xml version="1.0" encoding="utf-16"?>

按照鲍罗丁的说法更改我的开场代码,它仍然无效:

# parse the XML file
open(my $xmlIn, '<:encoding(UTF-16)', $xmlFile) or die "Couldn't open xml file '$xmlFile'. $!";
$twig->parse($xmlIn); # <= line 72

错误变为:

encoding specified in XML declaration is incorrect at line 1, column 30, byte 30 at /usr/lib/perl5/vendor_perl/5.14/x86_64-cygwin-threads/XML/Parser.pm line 187
 at ../../cv32/res/convert-xml-string2.pl line 72

2 个答案:

答案 0 :(得分:4)

显然,XML :: Twig(XML :: Parser)使用的XML解析器不支持 UTF-16。您需要首先将XML文档转换为支持的编码(例如UTF-8)。

例如,

use XML::LibXML qw( );

my $xml;
{
   open(my $fh, '<:raw', $qfn)
      or die $!;
   local $/;
   $xml = <$fh>;
}

{
   my $doc = XML::LibXML->new()->parse_string($xml);
   $doc->setEncoding('UTF-8');
   $xml = $doc->toString();
}

$twig->parse($xml);

更轻的解决方案是检测/期望UTF-16,解码文档(使用Encode的decode),使用正则表达式调整编码声明,然后编码文档(使用Encodes encode )。

答案 1 :(得分:0)

您的问题非常清楚,并且您没有显示为您工作的Perl代码的示例。所以我不得不做出很多猜测,而且我真的在黑暗中工作;但我希望这会有所帮助。

XML::Twig子类XML::Parser,它提供parse方法。文档说明了这个

parse(SOURCE [, OPT => OPT_VALUE [...]])
    The SOURCE parameter should either be a string containing the whole
    XML document, or it should be an open IO::Handle.

这意味着您可以按照自己的条件调用open,并将文件句柄传递给XML::Twig->parse方法。你的代码看起来应该是这样的

my $file_name = 'my_file.xml';

open my $xml_fh, '<:encoding(UTF-16)', $file_name
    or die qq{Unable to open "$file_name" for input: $!};

my $twig = XML::Twig->new;
$twig->parse($xml_fh);