Perl中使用.Net正则匹配平衡括号报错,求排查解决方法
Perl匹配平衡括号:解决.NET正则语法兼容问题
报错的核心原因是Perl正则引擎不支持.NET的(?<-name>)栈弹出语法。两者虽都支持命名捕获栈处理嵌套结构,但语法规则存在差异:
- .NET用
(?<-openp>)表示从openp栈中弹出一个元素 - Perl对应的栈弹出语法为
(?<openp>-)
修正后的完整代码
sub eat_parens($) { my $line = shift; if ($line !~ / \s*\( (?: [^\(\)] | (?<openp>\() | (?<openp>-)\) )+ (?(openp)(?!)) \)\s* /x) { return $line; } return $'; } sub testit2 { my $t1 = "(( (sdfasd)sdfsas (sdfasd) )sadf) ()"; my $t2 = eat_parens($t1); print "t1: $t1\n"; print "t2: $t2\n"; } testit2();
关键改动说明
- 替换栈弹出语法:将
(?<-openp>\))改为(?<openp>-)\),这是Perl中对命名捕获栈执行弹出操作的标准写法,每匹配一个右括号,就从openp栈中移除一条左括号的记录。 - 修复变量声明:给
$t2加上my声明,避免全局变量污染问题。
运行结果
执行修正后的代码会输出:
t1: (( (sdfasd)sdfsas (sdfasd) )sadf) () t2: ()
成功匹配并移除了最外层的平衡括号组,保留了末尾的()。
另外补充:Perl完全支持(?(openp)(?!))条件断言,它的作用是检查openp栈是否为空——如果栈不为空(括号未完全平衡),就通过(?!)触发匹配失败,确保只匹配完全平衡的括号结构。
内容的提问来源于stack exchange,提问作者pico
相关产品推荐
相关产品推荐

