有没有办法在不使用符号链接的情况下知道变量的名称?
use strict;
...
for ($var1, $var2, $var3)
{
die "NAME_OF_VAR is not defined" if !defined $_;
}
未定义var的输出:
“var [123]未定义为......”
答案 0 :(得分:2)
这是获取未定义变量致命警告的一种方法:
my ($var1, $var2, $var3) = 1..2;
{
use warnings FATAL => 'all';
my $test = "$var1 $var2 $var3";
}
<强>输出:强>
当上面的块中发生错误时,脚本将死亡。在这种情况下:
Use of uninitialized value $var3 in concatenation (.) or string at ...
我选择连接作为定义的测试,但它可能是在使用未定义变量时导致警告的任何操作。
答案 1 :(得分:2)
use strict;
use warnings;
my ($var1, $var2, $var3) = 1..2;
for( qw($var1 $var2 $var3) ) { print "$_ is undefined\n" if !defined eval($_) }
my
行来自TLP的示例,并具有以下输出:
$var3 is undefined
答案 2 :(得分:2)
PadWalker是解开别名的答案。但是,几乎在任何PadWalker都是答案的情况下,它可能是错误问题的答案。这是一个用于调试的模块之一,或者用于将自己绘制成角落后寻找出路的模块之一。如果它被用作不良设计的退出,也许重新考虑设计是一个更好的选择。在您的情况下,答案可能是已经提到过的答案:将警告提升为失败。
然而,该模块存在,有效,并且很有趣。
由于专门询问有关解开或检查别名的问题,以下是PadWalker能够将别名切换回原始变量的两个示例:
use strict;
use warnings;
use PadWalker qw( var_name );
my( $var1, $var2, $var3 ) = ( undef, undef, undef );
for ($var1, $var2, $var3) {
warn var_name( 0, \$_ ) . ' is not defined in "for" loop'
if !defined $_;
}
sub foo {
warn var_name( 1, \$_[0] ) . ' is not defined in sub foo()'
if !defined $_[0];
}
foo( $var1 );
产生的输出将是这样的:
$var1 is not defined in "for" loop at mytest.pl line 13.
$var2 is not defined in "for" loop at mytest.pl line 13.
$var3 is not defined in "for" loop at mytest.pl line 13.
$var1 is not defined in sub foo() at mytest.pl line 19.
注意如何在var_name( 0, ...
循环中指定for
,而在子例程中我们需要使用varname( 1, ...
向后移动一个额外的级别。
同样可能感兴趣的是given/when
语句不使用别名,尽管它们看起来像这样。因此,PadWalker无法追溯到given(...)
中指定的变量。
答案 3 :(得分:0)
我想你自己说过,你需要象征性的参考。请记住,这些并不是邪恶的,它们通常不是通常你想要的东西。在这种特定情况下,您正在进行一种元编程,您关心的是变量的名称。因此你可以这样做。
use strict;
...
for (qw/var1 var2 var3/)
{
no strict 'refs';
die "$_ is not defined" if !defined ${$_};
}
答案 4 :(得分:0)
考虑PadWalker模块:
#!/usr/bin/env perl
use warnings;
use strict;
use PadWalker qw(var_name);
my $foo = 123;
print var_name(0, \$foo), "\n"; # prints "$foo"
默认情况下未安装PadWalker,因此您需要使用系统上的cpan命令行工具进行安装。
当然,PadWalker很疯狂,可能不是你做任何事情的最佳方式,但偶尔玩弄它肯定很有趣。