使用什么而不是Smartmatch?

San*_*ing 4 regex perl

我刚刚升级到Perl 5.26.1,现在我得到了

Smartmatch is experimental at check_tr.pl line 67.
Run Code Online (Sandbox Code Playgroud)

有问题的代码在哪里

my @patterns = (qr/summary:\s+(.+?) in\s+(.+?) - average of\s+(.+?)$/,
        qr/summary:\s+(.+?) in\s+(.+) (.+? .+?)$/);
my $r = "";
opendir(DIR, $dir) or die $!;
while(my $file = readdir(DIR)) {

    next if ($file =~ m/^\./);
     open(F, '<', "$dir/$file") or die $!;

     if (<F> ~~ @patterns) {
         $r .= <F>;
...
Run Code Online (Sandbox Code Playgroud)

理想情况下,对代码的更改尽可能少.我应该怎么做而不是智能匹配?

amo*_*mon 6

只要说清楚你的意思.例如,如果要检查标题行是否与以下任何正则表达式匹配@patterns:

use List::Util 'any';
...
my $line = <F>;
if (any { $line =~ $_ } @patterns) { ... }
Run Code Online (Sandbox Code Playgroud)

虽然在这种情况下,预编译单个模式可能更为明智,例如:

my ($pattern) = map qr/$_/, join '|', @patterns;
...
if (<F> =~ $pattern) { ... }
Run Code Online (Sandbox Code Playgroud)

如果您的@patterns数组包含不同类型的数据,您可能希望选择不同的匹配运算符,例如==eq.如果@patterns不是所有相同的"类型"并且你真的想要smartmatch行为,你可以使警告静音并继续使用它:

use experimental 'smartmatch';
Run Code Online (Sandbox Code Playgroud)

但是,这可能会在未来没有进一步警告的情况下中断.


tjd*_*tjd 5

Smartmatch实验的原因在于,如果不引用文档就很难弄清楚它会做什么.即便如此,我们如何插入上述代码呢?

这是一个案例:

ARRAY1    ARRAY2     recurse on paired elements of ARRAY1 and ARRAY2[2]
            like: (ARRAY1[0] ~~ ARRAY2[0])
                    && (ARRAY1[1] ~~ ARRAY2[1]) && ...
Run Code Online (Sandbox Code Playgroud)

我们假设<F>在列表上下文中解释并在单个调用中清空?

或者这是一个案例:

 Any       ARRAY      smartmatch each ARRAY element[3]
            like: grep { Any ~~ $_ } ARRAY
Run Code Online (Sandbox Code Playgroud)

我猜第二个.在这种情况下,文档上面的代码段为您提供了一个优秀(和更清晰)的编码替代方案.假设@patterns包含正则表达式,你也可以更换~~使用=~.


如果您不喜欢grep文档中的替代方案,我建议您查看List::Util或者List::MoreUtils.两者都包含一个any充当短路的呼叫grep.或者,如果您尝试实施该ARRAY1 ARRAY2选项,则后一个库包含pairwise可能提供的调用.