perl 为键分配未定义的值

perl assigns key with undefined value

我有一段代码曾经是这样的:

$deepest{$xval} = $Evalue unless exists $deepest{$xval}; 

#some code

foreach (keys %deepest){
  print $datfh $_, "\t", $deepest{$_}, "\n";
}

然后我改成了

$deepest{$xval} = [$Evalue, $id] unless exists $deepest{$xval}[0];

#some more code

foreach (keys %deepest){
  print $datfh $_, "\t", $deepest{$_}[0], "\t", $deepest{$_}[1], "\n";
}

现在,当我之后打印散列时,我得到了很多警告:

Use of uninitialized value in print

我之前没有得到。

为什么新的哈希结构与旧的不同?我能做些什么来避免未初始化的条目吗?

更新:愚蠢的我,我没有在原始问题中包含实际导致错误的代码部分。现在它进来了,现在我也知道如何摆脱它,即将 exists $deepest{$xval}[0] 替换为 exists $deepest{$xval},第一种方法以某种方式创建了哈希条目。

试试这个代码

#should check exists of hash, not array
$deepest{$xval} = [$Evalue, $id] unless exists $deepest{$xval};
# some code
foreach (keys %deepest){
  # its good practice to use -> for arrayrefs and hashrefs ($deepest{$_} - arrayref)
  #and you should check $deepest{$xval}->[1] ( $id ) , maybe $id is undef
  warn '$id is not defined ' unless defined $deepest{$_}->[1];
  print $datfh $_, "\t", $deepest{$_}->[0], "\t", $deepest{$_}->[1],    "\n";
}

Exists 测试键是否存在。这很有用,但它可能不完全是您想要的,因为如果该键的 value 是 undef,它就可以工作。

您可能会发现 defined 执行您想要的操作:

my %hash = ( key => undef ); 

print "Key exists\n" if exists $hash{$key};
print "Key defined\n" if defined $hash{$key}; 

在你的情况下:

my %hash = ( key => [ ] ); 
print "Exists\n" if exists $hash{key};
print "Defined\n" if defined $hash{key}; 
print "Is true\n" if $hash{key}; 
print "Has values\n" if @{$hash{key}};

但是看看你的代码,我的想法是——你插入的匿名数组——它肯定总是至少有两个(定义的)元素吗?

因为解决该问题的一种明显方法是:

my %hash = ( key => [ "value", undef ] ); 
print $hash{key}[0], $hash{key}[1],"\n";

关于取消引用(因为它对于评论来说有点太大了)——你实际上只需要取消引用一次。

因为:

my $array_ref = [ 1, 4, 9 ]; 
print $array_ref,"\n"; #scalar value; 
print $array_ref -> [0],"\n"; #also scalar, from within array. 

如果您有:

my @array = ( [1, 4, 9], 
              [16, 25, 36], );
print "@array\n";
print \@array,"\n";
print $array[0],"\n"; #reference scalar - but because of the brackets
                      #perl knows you're referring to @array. 
print $array[0][1],"\n"; #scalar, but implicitly dereferenced.
print $array[0]->[1]; #dereferenced scalar, same as above.

最后两个案例是一样的 - 为什么?好吧,因为它必须是。 'parent' 数组 必须 是一个引用,因为数组的数组就是这样工作的,所以 perl 可以自动取消引用。