示例:我想删除重复的字符,$s
如下所示:
my $s = 'aabbbcbbac';
1 while $s =~ s/((.).*)\2/$1/;
print $s, "\n"; #prints abc
Run Code Online (Sandbox Code Playgroud)
是否有一种简单而简短的方法可以避免这个1 while
伎俩,并且只删除一个重复项s///g
?让它以某种方式"重新开始"?通过使用\G
或某种后视| -ahead?只是添加/g
不是这里的解决方案.
这可以通过可变长度的后视来完成,这是不允许的.但是可变长度的后视相当于输入反向的可变长度前瞻,所以我们可以使用这个技巧:
reverse
字符串,使用预测删除字符,然后reverse
再次
$t = reverse $s;
$t =~ s/(.)(?=.*\1)//sg;
$s = reverse $t;
Run Code Online (Sandbox Code Playgroud)
如果你有Perl 5.14或更高版本并且可以/r
在替换上使用修饰符,那么你就得到了
$s = reverse( reverse($s) =~ s/(.)(?=.*\1)//grs );
Run Code Online (Sandbox Code Playgroud)
非正则表达式的解决方案可以使用建split
,grep
并join
用查找散.但它可能没那么可读.
my $s = 'aabbbcbbac';
my %seen;
$s = join '', grep { !$seen{$_}++ } split //, $s;
print $s, "\n";
Run Code Online (Sandbox Code Playgroud)
这输出
abc
Run Code Online (Sandbox Code Playgroud)