有一个perl
错误,但你也有一个编程问题。不要依赖特殊变量的值,除非在它们设置后的立即语句中。立即存储它们的值。
当您遇到此类问题时,请查看数据。事实证明这是一个奇怪的问题,看起来像是处理捕获缓冲区的错误。
use v5.10;
use feature qw(unicode_strings);
my $text = "01";
if ($text =~ m/(\d+)/g)
{
say "\$1 [$1]: ", join ' ', map { sprintf '%04X', ord } split //, $1;
say 'Text: ', join ' ', map { sprintf '%04X', ord } split //, $text;
$text = "A$1";
say "\$1 [$1]: ", join ' ', map { sprintf '%04X', ord } split //, $1;
say 'Text: ', join ' ', map { sprintf '%04X', ord } split //, $text;
}
一切看起来都是正确的,直到您真正想要使用$1
来构建新字符串以分配给同一个变量,此时该值似乎消失了。请注意,分配后,$1
是不同的:
% perl5.12.2 test.pl
$1 [01]: 0030 0031
Text: 0030 0031
$1 [AA]: 0041 0041
Text: 0041 0041 0000
它也以一种奇怪的方式不同。perl
做了一些棘手的处理来记住字符串中的偏移量。在 v5.14 中,$1
仍然是字符串中的前两个字符:
% perl5.14.2 test.pl
$1 [01]: 0030 0031
Text: 0030 0031
$1 [A0]: 0041 0030
Text: 0041 0030 0031
$test
如果您分配给新变量而不是在同一语句中使用and ,则不会出现此问题$1
(这应该很好,但我们都知道“应该”通常是什么意思)。如果您立即捕获特殊变量的值,这也不是问题:
use v5.10;
use feature qw(unicode_strings);
my $text = "01";
if ($text =~ m/(\d+)/g)
{
my $one = $1;
say "\$1 [$1]: ", join ' ', map { sprintf '%04X', ord } split //, $1;
say 'Text: ', join ' ', map { sprintf '%04X', ord } split //, $text;
$text = "A$one";
say "\$1 [$1]: ", join ' ', map { sprintf '%04X', ord } split //, $1;
say 'Text: ', join ' ', map { sprintf '%04X', ord } split //, $text;
}
现在,即使 v5.12 也是正确的:
$ perl5.12.2 test.pl
$1 [01]: 0030 0031
Text: 0030 0031
$1 [A0]: 0041 0030
Text: 0041 0030 0031