Perl 延迟字符串插值

Perl deferred interpolation of string

我的情况是有一个分类脚本接收消息,将其与正则表达式列表进行比较,第一个匹配的设置存储桶。一些示例代码如下所示。

my $message = 'some message: I am bob';

my @buckets = (
    {
        regex => '^some message:(.*)',
        bucket => '"remote report: "',
    },
    # more pairs
);

foreach my $e (@buckets) {
    if ($message =~ /$e->{regex}/i) {
        print eval "$e->{bucket}";
    }
}

此代码将给出 remote report: I am bob。我一直在看这个,觉得必须有更好的方法来做到这一点,然后现在就完成了。特别是桶中的双引号('""')。有没有更好的方法来处理这个问题?

Perl 在计算该表达式时解析插值。为此,使用子程序就足够了,不需要 eval:

...
bucket => sub { "remote report: " },
...
print $e->{bucket}->();

请注意,您也有效地评估了您的正则表达式。您可以在散列中使用 pre-compiled 正则表达式对象,使用 qr// 运算符:

...
regex => qr/^some message:(.*)/i,
...
if ($message =~ /$e->{regex}/) {

您可以使用 sprintf 风格的格式字符串:

use strict;
use warnings;

my $message = 'some message: I am bob';

my @buckets = (
    {
        regex  => qr/^some message:(.*)/,
        bucket => 'remote report: %s',
    },
    # more pairs
);

foreach my $e (@buckets) {
    if (my @matches = ($message =~ /$e->{regex}/ig)) {
        printf($e->{bucket}, @matches);
    }
}