我很困惑访问我已解码的一些JSON数据的内容.这是一个例子
我不明白为什么这个解决方案有效,而我自己没有.我的问题在下面重述
my $json_raw = getJSON();
my $content = decode_json($json_raw);
print Data::Dumper($content);
Run Code Online (Sandbox Code Playgroud)
此时我的JSON数据已经转化为此
$VAR1 = { 'items' => [ 1, 2, 3, 4 ] };
Run Code Online (Sandbox Code Playgroud)
我的猜测告诉我,一旦解码,该对象将是一个散列,其中一个元素具有键items,数组引用作为值.
$content{'items'}[0]
Run Code Online (Sandbox Code Playgroud)
where $content{'items'}将获取数组引用,外部$...[0]将访问数组中的第一个元素并将其解释为标量.但这不起作用.我收到一条错误消息use of uninitialized value [...]
但是,以下工作正常:
$content->{items}[0]
Run Code Online (Sandbox Code Playgroud)
其中$content->{items}产生数组引用并[0]访问该数组的第一个元素.
问题
为什么不$content{'items'}返回数组引用?我甚至试过@{content{'items'}},想一想,一旦我得到了值content{'items'},它就需要被解释为一个数组.但是,我仍然收到未初始化的数组引用.
如何在不使用箭头运算符的情况下访问数组引用?
caj*_*ine 10
初学者对初学者的回答:)当然不是应该如此专业,但也许可以帮助你.
use strict; #use this all times
use warnings; #this too - helps a lot!
use JSON;
my $json_str = ' { "items" : [ 1, 2, 3, 4 ] } ';
my $content = decode_json($json_str);
Run Code Online (Sandbox Code Playgroud)
你写了:
我的猜测告诉我,一旦解码,该对象将是一个散列,其中一个元素具有关键项和数组引用作为值.
是的,它是一个哈希值,但decode_json返回一个引用,在本例中是对哈希的引用.(来自文档)
期望UTF-8(二进制)字符串并尝试将其解析为UTF-8编码的JSON文本,并返回结果引用.
在线
my $content = decode_json($json_str);
Run Code Online (Sandbox Code Playgroud)
您分配给SCALAR变量(不是哈希).
因为你知道:它是一个参考,你可以做下一个:
printf "reftype:%s\n", ref($content);
#print: reftype:HASH ^
#therefore the +------- is a SCALAR value containing a reference to hash
Run Code Online (Sandbox Code Playgroud)
它是一个hashref - 你可以转储所有密钥
print "key: $_\n" for keys %{$content}; #or in short %$content
#prints: key: items
Run Code Online (Sandbox Code Playgroud)
你也可以将"items"(arrayref)的值赋给标量变量
my $aref = $content->{items}; #$hashref->{key}
#or
#my $aref = ${$content}{items}; #$hash{key}
Run Code Online (Sandbox Code Playgroud)
但不是
#my $aref = $content{items}; #throws error if "use strict;"
#Global symbol "%content" requires explicit package name at script.pl line 20.
Run Code Online (Sandbox Code Playgroud)
该$content{item}请求从哈希值%content,你永远不定义/分配这样的变量.这$content是一个标量变量而不是哈希变量%content.
{
#in perl 5.20 you can also
use 5.020;
use experimental 'postderef';
print "key-postderef: $_\n" for keys $content->%*;
}
Run Code Online (Sandbox Code Playgroud)
现在再深入 - 到arrayref - 再次打印出引用类型
printf "reftype:%s\n", ref($aref);
#reftype:ARRAY
Run Code Online (Sandbox Code Playgroud)
打印数组的所有元素
print "arr-item: $_\n" for @{$aref};
Run Code Online (Sandbox Code Playgroud)
但同样不是
#print "$_\n" for @aref;
#dies: Global symbol "@aref" requires explicit package name at script.pl line 37.
{
#in perl 5.20 you can also
use 5.020;
use experimental 'postderef';
print "aref-postderef: $_\n" for $aref->@*;
}
Run Code Online (Sandbox Code Playgroud)
这是一个简单的规则:
my @arr; #array variable
my $arr_ref = \@arr; #scalar - containing a reference to @arr
@{$arr_ref} is the same as @arr
^^^^^^^^^^ - array reference in curly brackets
Run Code Online (Sandbox Code Playgroud)
如果你有$arrayref- 使用@{$array_ref}你想要的任何地方使用数组.
my %hash; #hash variable
my $hash_ref = \%hash; #scalar - containing a reference to %hash
%{$hash_ref} is the same as %hash
^^^^^^^^^^^ - hash reference in curly brackets
Run Code Online (Sandbox Code Playgroud)
如果你有$hash_ref- 使用%{$hash_ref}你想要的任何地方使用哈希.
对于整个结构,以下
say $content->{items}->[0];
say $content->{items}[0];
say ${$content}{items}->[0];
say ${$content}{items}[0];
say ${$content->{items}}[0];
say ${${$content}{items}}[0];
Run Code Online (Sandbox Code Playgroud)
打印相同的值1.
$content是哈希引用,因此您始终需要使用箭头来访问其内容。$content{items}会指代%content您没有的哈希。那就是从那里得到“未初始化值的使用”错误的地方。
| 归档时间: |
|
| 查看次数: |
13069 次 |
| 最近记录: |