【问题标题】:Not able to print value of this complex datastructure in perl无法在 perl 中打印这种复杂数据结构的值
【发布时间】:2014-07-17 08:11:27
【问题描述】:

问题在代码中解释为 cmets:

我有以下一段代码,我试图在其中创建一个散列,其中键本身是对其他数组的引用。

my @arr1=(1,2,3,4,5,6,7,8,9,10);
my @arr2=(1001,1002,1003);



$FILES_1=\@arr1;
$num1=2;
$FILES_2=\@arr2;
$num2=4;

@FILES=($FILES_1, $FILES_2);
@NUMS=($num1,$num2);
    fun (\@FILES,\@NUMS);





sub fun{

    my ($rFILES,$rNUMS) = @_;

    print "\n --${$rFILES}[0]->[2]  \n "; # This is same as below
    print "\n --$rFILES->[0]->[2]  \n "; # This is same as above

    my %hash=();

    $hash{$rFILES->[0]} = $rNUMS->[0];   

    my $test = $rFILES->[0];
    print "\nTEST : $test->[1]";

    my @key = keys %hash;
    print "\nKey 1 = $key[0]";   # This prints scalar value as below
    print "\ntest  = $test ";   # This prints scalar value as above

    print "\nKey 1->[1] = ${$key[0]}->[1]";  #PROBLEM : THIS DOESNT PRINT SAME AS BELOW
    print "\ntest->[1]  = $test->[1] ";  #THIS PRINTS AS EXPECTED.
}

输出:

 --3

 --3

TEST : 2
Key 1 = ARRAY(0x1bbb540)
test  = ARRAY(0x1bbb540)
Key 1->[1] =
test->[1]  = 2 

我们不应该保留哈希的键作为对某个数组的引用吗?为什么不打印值“2”?

【问题讨论】:

  • use strict; 然后use warnings;

标签: perl


【解决方案1】:

哈希键始终是字符串,您不能在其中存储引用。我也想不出你想要这个的理由。

您真的应该始终使用use strictuse warnings。如果你添加了这些并用my 正确声明了你的变量,你会得到一个警告:

Can't use string ("ARRAY(0x85e628)") as a SCALAR ref while "strict refs" in use

您正在使用的语法:

${$key[0]}

$key[0] 是对标量的引用。不是,它是一个带有引用地址的字符串,因为您不能将引用用作哈希键,它们会变成字符串。

更新:

你可能想要这样的东西:

my @filegroups = (
    { number => 1, files => ['file1','file2'] },
    { number => 2, files => ['file3'] },
);

访问为:

foreach my $filegroup ( @$filegroups ) {
    print "my number is $filegroup->{number}\n";
    print "   and I have ".scalar( @{ $filegroup->{ files } } )." files\n";
}

如果您需要额外的速度来按组号访问结构(除非您有数百个组或数千个访问,否则不要打扰),索引它们:

my %filegroupindexes = map { $_->{ number } => $_ } values @$filegroups;

然后你可以这样进入群:

print "there are ".scalar( @{ $filegroupindexes{ 1 }->{ files } } )." files in group 1\n";

最后提示,对于打印复杂的数据结构,Data::Printer 是我的最爱:

use Data::Printer colored => 1;
p( @filegroups );

【讨论】:

  • 感谢您的帮助 :) 。嗯,这是经常发生的情况。有各种文件组。并且每个组都有一个相关联的数字。因此,我制作了两个数组:一个包含对这些文件组的引用,另一个包含它们的关联编号。根据您的解释,我似乎可以将密钥作为“Key1”之类的字符串,并将它们的值作为 $rFILES->[0] 和 $rNUMS->[0]。但是将名为“Key1”的键绑定到这些值没有任何意义。 Key1 对这些值没有任何意义。然而,将 $rFiles 与 rNUMS 绑定绝对是有意义的。
  • 十多年来,我一直在专业地使用 Perl,例如系统管理类型的脚本、数据和日志处理、数据库交互和驱动 Web 服务器后端,但我从来没有觉得需要将字符串以外的内容存储在哈希键中。我认为这是糟糕的设计,并且有一些简单的方法可以解决它。我不完全确定你想通过使用数据作为哈希键来实现什么,但我绝对确定你不需要它。
  • 我同意你的观点,这可能是糟糕的设计。但我现在不知道如何处理这个问题。
【解决方案2】:

如果要将引用用作哈希键,则需要 Tie::RefHash

【讨论】:

  • 没有人需要Tie::RefHash
  • @friedo:请解释原因?
  • 只是我的讽刺方式,如果您尝试将引用存储在哈希键中,那么您可能以错误的方式解决了问题。 Leeft 为这个问题提供了一个很好的解决方案。
  • 哦,好的。 [还有 7 个]
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-08-24
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-06-21
相关资源
最近更新 更多