Perl YAML 模块无法识别标量类型 [英] Perl YAML module does not recognize types of scalars

查看:50
本文介绍了Perl YAML 模块无法识别标量类型的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我加载以下 .yaml 文件

I load the following .yaml file

foo : bar
s : 1
hx: 0x34

用这段代码:

use YAML qw(LoadFile Dump); 
use Data::Dumper; 
my $d=LoadFile("test.yaml"); 
print Dumper($d);
print "x        =", $d->{hx},"\n";
print "x/2      =", $d->{hx}/2,"\n";
print "hex(x)/2 =", hex($d->{hx})/2,"\n";

输出是

Output:
> ./yaml.pl
$VAR1 = {
          'foo' => 'bar',
          'hx' => '0x34',
          's' => '1'
        };
x        =0x34
x/2      =0
hex(x)/2 =26

这意味着它将所有标量视为字符串,这是我没想到的.从 CPAN 的 YAML 文档 http://metacpan.org/pod/YAML 我认为这是由隐式标记处理,模块将识别十六进制数.

This means it treats all scalars as strings, which I did not expect. From the YAML documentation at CPAN http://metacpan.org/pod/YAML I assumed that this is handled by implicit tagging and that the module would recognize the hex number.

有人知道怎么做吗?

推荐答案

如果你检查 loader 类,你会发现 _parse_inline 子有几个分支用于序列、映射、单双-quoted 字符串和其他一些情况.您需要做的就是为以 0x 开头的值添加一个分支.我写了那个分支和一个子来处理 YAML 0.900.0 的十六进制值.我尝试了一些基本输入,它似乎可以满足您的需求.如果它也适用于您,请考虑提交补丁.

If you examine the loader class, you will find that the _parse_inline sub has a few branches for sequences, mappings, single and double-quoted strings and a few other cases. All you need to do is add a branch for values starting with 0x. I wrote that branch and a sub for dealing with hex values for YAML 0.900.0. I tried with some basic input, and it seems to do what you wanted. If it works for you as well, consider submitting the patch.

use YAML qw(LoadFile Dump); 
use Data::Dumper; 
my $d=LoadFile("test.yaml"); 
$d=LoadFile("test.yaml"); 
print Dumper($d);
print "x        =", $d->{hx},"\n";
print "x/2      =", $d->{hx}/2,"\n";
print "hex(x)/2 =", hex($d->{hx})/2,"\n";



$d=LoadFile("sym1.yaml"); 
print Dumper($d);

print "dodo[4]  =", $d->{dodo}->{doto}[4], "\n";
print "dodo[3]  =", $d->{dodo}->{doto}[3], "\n";

sym1.yaml

"symfony 1.0":
  PHP:    5.0
  Propel: 1.2
"symfony 1.2":
  PHP:    5.2
  Propel: 1.3

dodo:
  doto: [1,23,4, 0x34, 0x16 ]
  dozo: [1,23,4, 0x12, 0x11 ]
  dofo: { a: 2,  358: 0x166, 255: 0xff, 255: 0xFF}
ffa: 0xFfA

$ perl dump.pl

$VAR1 = {
          'foo' => 'bar',
          'hx' => 52,
          's' => '1'
        };
x        =52
x/2      =26
hex(x)/2 =41
$VAR1 = {
          'ffa' => 4090,
          'symfony 1.2' => {
                           'PHP' => '5.2',
                           'Propel' => '1.3'
                         },
          'dodo' => {
                    'dofo' => {
                              'a' => '2',
                              '255' => 255,
                              '358' => 358
                            },
                    'dozo' => [ '1','23', '4', 18, 17 ],
                    'doto' => [ '1', '23', '4', 52, 22 ]
                  },
          'symfony 1.0' => {
                           'PHP' => '5.0',
                           'Propel' => '1.2'
                         }
        };

doto[4]  =22
doto[3]  =52

YAML 0.900.0 补丁

diff --git a/Loader.pm b/Loader.pm
index 3bf20c7..d7096df 100644
--- a/Loader.pm
+++ b/Loader.pm
@@ -437,6 +437,10 @@ sub _parse_inline {
         $node = $self->_parse_inline_single_quoted();
         $node = $self->_parse_implicit($node) if $implicit;
     }
+    elsif ($self->inline =~ /^0x/) {
+        $node = $self->_parse_inline_single_hex();
+        # do something if implicit?
+    }
     else {
         if ($top) {
             $node = $self->inline;
@@ -541,6 +545,21 @@ sub _parse_inline_single_quoted {
     return $node;
 }
 
+# Parse the inline hex value
+sub _parse_inline_single_hex {
+    my $self = shift;
+    my $node;
+    if ($self->inline =~ /^0x([A-Fa-f0-9]+)(,?.*)?$/) {
+        $node = hex($1);
+        $self->inline($2);
+        $node =~ s/''/'/g;
+    }
+    else {
+        $self->die('YAML_PARSE_ERR_BAD_HEX');
+    }
+    return $node;
+}
+
 # Parse the inline unquoted string and do implicit typing.
 sub _parse_inline_simple {
     my $self = shift;

这篇关于Perl YAML 模块无法识别标量类型的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆