我有一个方法可以使用java验证字符串中准确的开括号和右括号。此方法将用于解析数学表达式,因此对括号进行平衡非常重要。出于某种原因,它在这两个运行中都返回false:
System.out.println(parChecker("(()")); // returns false :-)
System.out.println(parChecker("((()))")); // returns false :-( WHY??
以下是使用堆栈解决问题的方法。这里出了点问题,因为它对于一组平衡的括号也会返回错误。有什么问题?提前谢谢。
public static boolean parChecker(String str) {
String[] tokens = str.split("");
int size = tokens.length;
Stack theStack = new Stack(size);
int index = 0;
boolean balanced = true;
while ((index < size) && balanced) {
String symbol = tokens[index];
if (symbol.equals("(")) {
theStack.push(symbol);
} else {
if (theStack.isEmpty()) {
balanced = false;
} else {
theStack.pop();
}
}
index++;
}
if (balanced && theStack.isEmpty()) {
return true;
} else {
return false;
}
}
这是我正在使用的堆栈类:
public class Stack {
private Object [] stack;
private int maxSize = 0;
private int top;
public Stack(int size){
maxSize = size;
stack = new Object[maxSize];
top = -1;
}
public void push(Object obj){
top++;
stack[top] = obj;
}
public Object pop(){
return stack[top--];
}
public Object peek(){
return stack[top];
}
public boolean isEmpty(){
return (top == -1);
}
public boolean isFull(){
return (top == maxSize -1);
}
}
答案 0 :(得分:6)
当前的问题是这个
String[] tokens = str.split("");
如果您使用java 1.7
或更少,则首先给出char =“”,因此您将退出循环,因为堆栈为空...
注意:这已在java 1.8
split difference between java 1.7 and 1.8
更改为:
char[] tokens = str.toCharArray();
我想你需要考虑这样一个事实:在你的第一个(
之前可能有字符,而你可能有其他字符(
和)
答案 1 :(得分:3)
据我所知,代码没有问题(证明它是Java 7特定的问题.. )。
我想提供一种替代方法,但出于教育目的,它更短,并且容忍其他角色存在:
public static boolean parChecker(String str) {
Stack stack = new Stack(str.length());
for (char c : str.toCharArray())
switch (c) {
case '(':
stack.push(c);
break;
case ')':
if (stack.isEmpty() || stack.pop() != Character.valueOf('('))
return false;
}
return stack.isEmpty();
}
根据要求,这是另一个不使用堆栈的解决方案:
public static boolean parChecker(String str) {
str = str.replaceAll("[^()]", "");
while (str.contains("()"))
str = str.replace("()", "");
return str.isEmpty();
}
另外还有一条道路:@ FredK的算法:
public static boolean parChecker(String str) {
int depth = 0;
for ( char c : str.toCharArray() )
if ( ( depth += c == '(' ? 1 : c == ')' ? -1 : 0 ) < 0 )
return false;
return depth == 0;
}