"Programming Perl"中的"evaluated directly for a Boolean result, and no smartmatching occurs"是什么意思?



在"编程Perl"一书中有一个片段(剪切):

默认情况下,当(EXPR)被视为$_;(即$_ ~~ EXPR)的隐式智能匹配时。然而,如果对when的EXPR自变量是下面列出的10种例外形式之一,它被直接评估为布尔结果,并且没有发生智能匹配:

  1. 。。。

  2. 正则表达式匹配形式为/REGEX/、$foo=~/REGEX/或$foo=~经验。

evaluated directly for a Boolean result是什么意思?

示例:

#!/usr/bin/perl
use v5.14;
my @a = ('aaa', 'bbb', 'ccc');
given(@a) {
    when (/a/) { say '@a contains an a'; }
    default    { say '@a does not contain an a' }
}

当我运行它时,输出会随时间变化:

@a does not contain an a
@a contains an a
@a does not contain an a
@a does not contain an a

我不明白这里发生了什么,有人能这么乐意帮忙吗?

提前感谢。

仔细阅读文档:

另一个有用的快捷方式是,如果将文字数组或哈希用作"给定"的自变量,它就变成了一个引用。所以例如,"giving(@foo)"与"given(\\foo))"相同。

因此,given (@a)变为given(@a)。没有智能匹配,因为您使用when (/a/),所以您正在尝试匹配

@a =~ /a/

引用已字符串化。它有时包含"a",如ARRAY(0x9a4e7f8),但通常不包含:-)

documentatiom意味着when (/a/)不等价于if ($_ ~~ /a/),后者将检查任何数组元素是否与正则表达式匹配,而等价于if ($_ =~ /a/),后者只是检查标量$_是否匹配。

将数组传递给given时,它会为该数组分配引用。因为(正如文档所说)没有使用智能匹配运算符,所以像when (/a/)这样的条件等价于@a =~ /a/

因为在尝试正则表达式匹配之前,引用将被字符串化,所以它将比较类似ARRAY(0x61c6dc)的内容。由于您正在字符串中查找小写的a,因此如果字符串中的十六进制数组位置恰好包含a,则情况会如此。根本不是你想要的!

when(/a/)确实做了一些类似if (/a/)的事情,而不是像if ($_ ~~ /a/)。如果您想要后者,则应该使用when (qr/a/)

when ('a')
when (123)

是的缩写

when ($_ ~~ 'a')
when ($_ ~~ 123)

这份名单是这种行为的例外。你特别询问的是

when (/b/)
when ($x =~ /c/)

不是的缩写

when ($_ ~~ /b/)
when ($_ ~~ $x =~ /c/)

它们具有正常意义(when之外),即

when ($_ =~ /b/)
when ($x =~ /c/)

最新更新