【问题标题】:Binary Expression tree, emptyStackException (java)二进制表达式树,emptyStackException (java)
【发布时间】:2018-01-19 15:21:52
【问题描述】:

我已经编写了一个代码,它从给定的字符串表达式创建一个二叉表达式树:

public ExprIF buildExpressionTree(String s)
{
    for(int i = 0; i<s.length(); i++)
    {
        if(Character.isDigit(s.charAt(i)) || isOperator(s.charAt(i)))//containOp(s,i))
        {
            treeRoot = new Expr(s.charAt(i)); 
            stack.push(treeRoot);
        }           
        else if(s.charAt(i) == '(')
        {
            //do nothing
        }   
        else
        {
            rightSubTree = stack.pop();
            treeRoot = stack.pop();
            leftSubTree = stack.pop();
            treeRoot.setLeft(leftSubTree);
            treeRoot.setRight(rightSubTree);
            stack.push(treeRoot);
        }           
    }
    return stack.pop();
} 

当我在纸上测试它时,它运行良好。问题是这个错误:

Exception in thread "main" java.util.EmptyStackException
    at java.util.Stack.peek(Stack.java:102)
    at java.util.Stack.pop(Stack.java:84)
    at builder.TreeBuilder.buildExpressionTree(TreeBuilder.java:49)
    at builder.TreeBuilder.build(TreeBuilder.java:29)
    at Main.main(Main.java:12)

这个错误的原因是什么?

【问题讨论】:

  • 您可以分享您正在使用的示例输入吗?
  • 运算符是二元运算符:*、+、-、/、^、% 此方法返回它看到给定字符等于这些二元运算符之一

标签: java tree expression binary-tree


【解决方案1】:

您的问题是您提供的输入字符串,它有空格,所以循环的第三次迭代得到一个空格字符并移动到最后一个 else 语句。此时堆栈为空,因此您得到StackEmptyException。尝试使用 ((1+2)*3) 输入字符串。

在您的逻辑中,当执行最后一个 else 时,您至少必须有 3 个元素(两位数和一个操作数)。

您的代码中的另一个问题是')' 不考虑右大括号,因此对于输入 "((1+2)*3)" else 语句将看到以下堆栈条目:

[1, +, 2]
[), *, 3]

你也需要跳过')',最好写一个检查跳过字符的方法:

private boolean skip(char c)
    {
        return c==')' || c=='(' || c==' ';
    }

现在在else if更改逻辑:

else if(skip(s.charAt(i))
        {
            //do nothing, its a skip character
        }  

【讨论】:

  • 你是对的,所以我应该有类似 => else if(s.charAt(i) == '(' || s.charAt(i) == ' ') 在我的第二否则
  • 是的,但最好以单独的方法移动字符跳过逻辑,请参阅上面的编辑答案。如果它解决了您的问题,您可以接受答案。
  • 现在我的项目已经完成了。但是为了测试,我遇到了另一个问题,那就是当我得到 ( ( 1 + 2 ) * 3.5 ) => 它给了我错误的地方,我得到了 3.5 => 我知道问题是逐个字符地阅读。谁能帮忙?
【解决方案2】:

对于您提供的输入,您的代码只是忘记处理空格。

解决方案1:添加以下代码以删除所有空格。

s = s.replaceAll("\\s", "");

解决方案 2:替换

}

else
{
rightSubTree = stack.pop();
/* ... ... */

通过

} else if (c == ')'){
    rightSubTree = stack.pop();
    /* ... ... */

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-08-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-07-25
    相关资源
    最近更新 更多