这可以通过正则表达式替换来完成。但它仅限于简单的情况,并且在引用的字符串中没有嵌套的括号或括号,否则它会中断。
use strict;
use warnings;
my $string = "['-1XA0.55B',40,100,DU(26,3,20),100.00, DU(26,32,99) ]";
$string =~ s/\([^()]*\)/$& =~ tr|,|.|r/ge;
print $string;
输出:
['-1XA0.55B',40,100,DU(26.3.20),100.00, DU(26.32.99) ]
我们所做的只是匹配一个文字括号,然后是可选的非括号,然后是另一个括号。然后我们获取匹配的字符串$& 并对其执行音译,将, 更改为.,然后将其作为替换的替换部分返回。 tr/// 上的 /r 修饰符不会尝试更改 $&(这是只读的,所以我们不能),而只是返回结果字符串而不更改 $&。替换 /ge 上的修饰符表示全局匹配,并且替换部分(音译)应作为代码进行评估。
这也可以用更详细的代码来完成,虽然更复杂,但更能说明问题
use strict;
use warnings;
my $string = "['-1XA0.55B',40,100,DU(26,3,20),100.00, DU(26,32,99) ]";
while ($string =~ /\([^()]*\)/g) {
my $pos = pos($string); # remember where we were
my $match = $&; # copy the matched string
$match =~ tr/,/./; # alter the copy
$string = $` . $match . $'; # reassemble the string
pos($string) = $pos + length($match); # reset position
}
print $string;
这里有很多代码是为了模拟替换正则表达式的工作原理。请注意,由于我们更改了$string 变量,因此我们必须在最后重置匹配位置,从而重置迭代器。变量$` $& $' 分别指的是赛前、比赛和赛后变量。引用最近的正则表达式匹配的匹配。