如何解释替换?

时间:2012-11-29 03:39:54

标签: perl

$test='abc="def"';
$replacement='$1="ghj"';
$test =~ s/(.+)="(.+)"/"$replacement/;
print $test;

打印:

$1=ghj

如何处理$replacement被解释?

2 个答案:

答案 0 :(得分:6)

您将/e修饰符添加到正则表达式中。您还需要修改替换字符串,以便正确评估它。插值变量需要双重评估。

my $test='abc="def"';
my $replacement='"$1=ghj"';
$test =~ s/(.+)="(.+)"/$replacement/ee;
print $test;

<强>输出:

abc=ghj

应该注意的是,这有些不安全,特别是如果其他人可能影响您的更换价值。然后他们可以在你的系统上执行任意代码。

答案 1 :(得分:4)

这个问题大约有3个答案。

  • 您的替换“字符串”实际上是在匹配时要评估的代码,以生成替换字符串。也就是说,它更好地表示为一个函数:

my $test = 'abc="def"';
my $replacement = sub { $1 . '="ghj"' };
$test =~ s/(.+)="(.+)"/$replacement->()/e;
print $test;
  • 如果您不需要任意Perl表达式的全部功能(或者您的替换字符串来自外部源),您还可以将其视为要使用匹配结果填充的模板。有一个模块以类似JavaScript的replace函数的形式封装了这个函数,Data::Munge

use Data::Munge qw(replace);
my $test = 'abc="def"';
my $replacement = '$1="ghj"';
$test = replace $test, qr/(.+)="(.+)"/, $replacement;
print $test;
  • 最后,您可以将Perl代码表示为字符串eval'd。这不仅效率低,而且还充满引用问题(您必须确保$ replacement中的所有内容都是语法上有效的Perl)和安全漏洞(如果在运行时生成$ replacement,特别是如果它来自外部源)。我最不喜欢的方法:

my $test = 'abc="def"';
my $replacement = '$1 . "=\\"ghj\\""';
$test =~ s/(.+)="(.+)"/eval $replacement/e;
print $test;

s//eval $foo/e部分也可以写成s//$foo/ee。我不喜欢这样做,因为eval是邪恶的,不应该比现在更隐蔽。 )