我试图按照跟踪变量用法的顺序绑定哈希(或hashref).
一切都适用于简单的情况,但当我尝试在一些真正的代码上使用我的模块时,我遇到了这个错误:
hash- or arrayref expected (not a simple scalar,use allow_nonref to allow this)
use Tie::Hash::Usages; use JSON; my @arr = ( { key1 => "ac",key2 => 12,key3 => 12 },); my %tied_hash; tie %tied_hash,'Tie::Hash::Usages'; $tied_hash{key1} = \@arr; my @val = $tied_hash{key1}; print encode_json(\@val)."\n\n"; #this works print encode_json($tied_hash{key1}); #this doesn't
相同的代码使用普通哈希.
在第二种情况下我也需要这个工作,代码库是巨大的,我不想改变它或怀疑某些地方某些东西在某些特定情况下不起作用.
Usages.pm(简体)
package Tie::Hash::Usages; use strict; use warnings; use Tie::Hash; use vars qw(@ISA); @ISA = qw(Tie::StdHash); sub TIEHASH { my ($class,$tracker,$filename) = @_; my %hash; bless \%hash,$class; } sub STORE { my ($self,$key,$val) = @_; $self->{$key} = $val; } sub DELETE { my ($self,$key) = @_; delete $self->{$key}; } sub FETCH { my ($self,$key) = @_; return $self->{$key}; } sub DESTROY { my $self = shift; } 1;
perl版本:v5.18.2
解决方法
最小的演示:
use JSON::XS qw( encode_json ); use Tie::Hash qw( ); our @ISA = 'Tie::StdHash'; { tie my %tied,__PACKAGE__; $tied{data} = { a => 1 }; encode_json($tied{data}); # Exception: hash- or arrayref expected ... }
JSON是JSON :: PP(默认)或JSON :: XS(如果找到)的前端.这是JSON :: XS的问题.
很多XS代码都没有处理魔法变量(这是$tied {EXPR}返回的内容),虽然JSON :: XS自1.2版以来已经处理了神奇的值,但它并没有直接传递给encode_json的值.
encode_json(my $non_magical = $tied{data})