Java的标准正则表达式引擎基于Perl 5的正则规范实现,并未支持PCRE扩展中的递归匹配语法(?R),因此无法直接通过正则完成嵌套括号、嵌套标签这类需要递归回溯的匹配场景,需要采用替代方案模拟实现平衡括号的匹配逻辑。

为什么Java正则不支持(?R)
递归匹配语法(?R)属于PCRE(Perl Compatible Regular Expressions)的扩展特性,允许正则表达式在匹配过程中递归调用自身,非常适合处理嵌套结构的匹配。但Java内置的java.util.regex包实现的是Perl 5的基础正则规范,没有引入PCRE的扩展特性,因此不支持(?R)语法,使用时会直接抛出正则语法错误。
方案一:基于栈的手动匹配实现
最通用的平衡括号匹配方案是通过栈数据结构手动处理字符遍历,遇到左括号入栈,遇到右括号判断栈顶是否为对应左括号,匹配则出栈,最终栈为空说明括号完全平衡。
以下是完整的实现代码示例:
import java.util.Stack;
public class BalanceBracketChecker {
public static boolean isBalance(String input) {
Stack<Character> stack = new Stack<>();
// 遍历输入字符串的每个字符
for (int i = 0; i < input.length(); i++) {
char c = input.charAt(i);
// 左括号入栈
if (c == '(' || c == '[' || c == '{') {
stack.push(c);
} else if (c == ')' || c == ']' || c == '}') {
// 右括号时栈为空说明不匹配
if (stack.isEmpty()) {
return false;
}
char top = stack.pop();
// 判断括号是否对应
if (!isMatch(top, c)) {
return false;
}
}
}
// 最终栈为空说明所有括号都匹配完成
return stack.isEmpty();
}
private static boolean isMatch(char left, char right) {
return (left == '(' && right == ')')
|| (left == '[' && right == ']')
|| (left == '{' && right == '}');
}
public static void main(String[] args) {
String test1 = "(a(b)c)";
String test2 = "(a(b)c";
System.out.println(test1 + " 是否平衡:" + isBalance(test1));
System.out.println(test2 + " 是否平衡:" + isBalance(test2));
}
}
方案二:有限状态正则模拟匹配
如果必须使用正则表达式实现简单的嵌套括号匹配,可以通过有限状态的正则语法模拟两层以内的嵌套匹配,这种方式仅适用于嵌套层级固定的场景,无法处理任意层级的嵌套。
以下是匹配两层嵌套小括号的正则示例:
import java.util.regex.Pattern;
import java.util.regex.Matcher;
public class RegexBalanceMatch {
public static void main(String[] args) {
// 正则匹配最多两层嵌套的小括号内容
String regex = "\([^()]*(\([^()]*\)[^()]*)*\)";
Pattern pattern = Pattern.compile(regex);
String test1 = "(a(b)c)";
String test2 = "(a(b(c)d)e)";
Matcher matcher1 = pattern.matcher(test1);
Matcher matcher2 = pattern.matcher(test2);
if (matcher1.find()) {
System.out.println("test1匹配结果:" + matcher1.group());
} else {
System.out.println("test1无匹配结果");
}
if (matcher2.find()) {
System.out.println("test2匹配结果:" + matcher2.group());
} else {
System.out.println("test2无匹配结果");
}
}
}
两种方案对比
| 方案 | 适用场景 | 优点 | 缺点 |
|---|---|---|---|
| 栈手动匹配 | 任意层级嵌套括号匹配 | 支持任意嵌套层级,逻辑清晰易扩展 | 需要额外编写逻辑代码,不是纯正则实现 |
| 有限状态正则 | 固定层级嵌套括号匹配 | 纯正则实现,代码简洁 | 仅支持固定层级,嵌套层级变化需要修改正则 |
注意事项
- 栈方案处理时需要注意空字符串、无括号字符串的边界情况,避免空指针或逻辑错误。
- 有限状态正则方案如果需要支持更多层级,正则语法会非常复杂,可读性会大幅下降,不建议使用。
- 如果匹配的是HTML标签这类嵌套结构,建议优先使用专门的HTML解析库,不要尝试用正则或栈模拟匹配,避免遗漏特殊场景。