在Perl子例程调用中,不匹配的正则表达式会发生什么?

时间:2015-06-18 18:37:18

标签: perl

我试图弄清楚子程序调用中非匹配正则表达式发生了什么。考虑一下这个脚本:

sub routine{
    print Dumper(\@_);
}

my $s = 'abc123';

# These pass a single element to &routine
&routine( $s =~ /c/ );      # 1. passes (1)
&routine(2 == 3);           # 2. passes ('')
&routine(3 == 3);           # 3. passes (1)

# The following two calls appear to be identical 
&routine( $s =~ /foobar/ ); # 4. passes ()
&routine();                 # 5. passes ()

在上面的脚本中,数字1,2和3都将单个值传递给&routine。我很惊讶4号没有传递错误值,而是根本没有传递任何东西!

由于条件中相同类型的签名无效,因此非匹配正则表达式根本不会评估为任何内容:

# This is fine
if( $s =~ /foobar/ ){
   print "it's true!\n";
}

# This is a syntax error
if( ){
   print "Hmm...\n"; # :/
}

在子程序调用中使用非匹配正则表达式时会发生什么?此外,&routine是否有可能弄清楚是否使用不匹配的正则表达式调用它,而不是根本没有?

1 个答案:

答案 0 :(得分:3)

在列表上下文中使用匹配运算符=~时,它返回匹配列表。如果没有匹配项,则此列表为空(也称为空列表),并将空列表传递给您的子routine,这会导致@_为空。

如果您明确要传递“此表达式是否返回任何匹配项?”的false值。你需要在标量上下文中执行你的匹配。您可以使用scalar关键字

执行此操作
&routine( scalar $s =~ /foobar/ );

会将值''(false)传递给您的routine子。调用没有任何参数的sub有效地传递了这个空列表,因此你的最终示例将被正确编写:

if ( () ) {
   print "Hmm...\n";
}

这不是语法错误,因为在Perl 0''()都表示false。