EmptyStackException(空堆栈异常)
问题描述
此 EmptyStackException 继续弹出.不知不觉中,我的堆栈中没有任何内容,而是用户输入的第一个元素.但是,我不确定代码的缺陷在哪里.(很多地方)但我只需要修复这个错误.
This EmptyStackException continues to pop up. Obliviously there is nothing in my stack, but the first element that the User inputs. However, I am not sure where the code is flawed. (many spots) but I just need to fix this error.
import java.util.*;
public class stacks2 {
public static void main (String []args){
System.out.printf("Enter a math equation in reverse polish notation:
");
//Create stack of Strings
Stack<String> rpnStack = new Stack<String>();
//Create Scanner
Scanner input = new Scanner(System.in);
//String in = input.next();
while(input != null) {
String in = input.next();
// Tokenize string based on spaces.
StringTokenizer st = new StringTokenizer(in, " ", true);
while (st.hasMoreTokens()) {
rpnStack.push(st.nextToken());
}
//Send stack to Calculation Method
calculate(rpnStack);
}
}
public static void calculate(Stack<String> stack) {
// Base case: stack is empty => Error, or finished
if (!stack.isEmpty())
// throw new StackUnderflowException("Empty Stack");
// Base case: stack has 1 element, which is the answer => finished
if (stack.size() == 1)
System.out.printf("Finished, Answer: %s
",stack.peek());
// Recursive case: stack more elements on it.
if (stack.size() > 1){
String temp1 = stack.peek();
stack.pop();
String temp2 = stack.peek();
stack.pop();
String temp3 = stack.peek();
stack.pop();
if (temp3.equals("+")){
float resultant = Float.parseFloat(temp1) + Float.parseFloat(temp2);
stack.push(String.valueOf(resultant));
//System.out.println(resultant);
calculate(stack);
}
if (temp3.equals("-")){
float resultant = Float.parseFloat(temp1) - Float.parseFloat(temp2);
stack.push(String.valueOf(resultant));
//System.out.println(resultant);
calculate(stack);
}
else if (temp3.equals("*")){
float resultant = Float.parseFloat(temp1) * Float.parseFloat(temp2);
stack.push(String.valueOf(resultant));
//System.out.println(resultant);
calculate(stack);
}
else if (temp3.equals("/")){
float resultant = Float.parseFloat(temp1) / Float.parseFloat(temp2);
stack.push(String.valueOf(resultant));
//System.out.println(resultant);
calculate(stack);
}
else{
System.out.printf("Something severely has gone wrong.");
}
}
}
}
输入和错误:
:~ Home$ java stacks2
Enter a math equation in reverse polish notation:
4 5 * 6 -
Finished, Answer: 4
Exception in thread "main" java.util.EmptyStackException
at java.util.Stack.peek(Stack.java:85)
at stacks2.calculate(stacks2.java:41)
at stacks2.main(stacks2.java:22)
显然,这只是采用第一个元素,这让我认为我在 17 处的 while 循环是原因.有什么见解吗?
clearly this is only taking the first element which makes me think my while loop at 17 is the cause. Any insight?
推荐答案
String in = input.next();
读取你一个单词,然后你试图标记那个单词.也许你的意思是 String in = input.nextLine();
String in = input.next();
reads you one word, then you are trying to tokenise that word. Perhaps you meant String in = input.nextLine();
http://docs.oracle.com/javase/1.5.0/docs/api/java/util/Scanner.html#next()http://docs.oracle.com/javase/1.5.0/docs/api/java/util/Scanner.html#nextLine()
此外,您的代码中有这两行.
Also, you have these two lines in your code.
if (!stack.isEmpty())
// throw new StackUnderflowException("Empty Stack");
这是完全错误的.如果没有大括号,if
会影响下一条语句.这不是评论 - 它是以下 if.
This is plain wrong. Without its curly braces, the if
affects the next statement. It is not the comment - it is the following if.
这个:
if (!stack.isEmpty())
// throw new StackUnderflowException("Empty Stack");
// Base case: stack has 1 element, which is the answer => finished
if (stack.size() == 1)
System.out.printf("Finished, Answer: %s
",stack.peek());
等价于:
if (!stack.isEmpty())
if (stack.size() == 1)
System.out.printf("Finished, Answer: %s
",stack.peek());
还有这个:
if (!stack.isEmpty() && stack.size() == 1){
System.out.printf("Finished, Answer: %s
",stack.peek());
}
道德:始终使用带有 if
的大括号,并且不要注释掉断言.即使您确实注释掉了断言,也要完整地注释它们,而不是其中的一半,尤其是当另一半是未加括号的 if 时.
Moral: always use curly brackets with an if
AND don't comment out assertions. Even if you do comment out assertions, comment them completely, and not one half of them, epecially when the other half is an un-bracketed if.
第三,你的逻辑有缺陷.你这样做:
Third, your logic is flawed. You do this:
将所有符号推入堆栈,然后弹出前三个并将它们视为运算符和两个数字.这将适用于一些输入如果您改用队列.
push all symbols to the stack, then pop the top three and consider them an operator and two numbers. This will work with some inputs if you use a queue instead.
4 5 * 6 -
按照您的逻辑,这将弹出 * 6 -
并崩溃.如果您使用队列,它会工作在这种情况下
By your logic, this will pop * 6 -
and crash. If you use a queue, it will work in this case
4 5 * 6 -
20 6 -
14
但不是这种情况:
(1+1)*(1+1)
express as RPN
1 1 + 1 1 + *
2 1 1 + *
接下来,你弹出 2 1 1 并崩溃.
Next, you pop 2 1 1 and crash.
相反,你应该怎么做:
Read the input. For each symbol:
if it is a number,
push it on the stack.
else,
pop two numbers from the stack,
perform the operation and
push the result.
这篇关于空堆栈异常的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持编程学习网!
本文标题为:空堆栈异常
基础教程推荐
- 在螺旋中写一个字符串 2022-01-01
- Java 中保存最后 N 个元素的大小受限队列 2022-01-01
- 如何使用 Stream 在集合中拆分奇数和偶数以及两者的总和 2022-01-01
- 由于对所需库 rt.jar 的限制,对类的访问限制? 2022-01-01
- 如何使用 Eclipse 检查调试符号状态? 2022-01-01
- 如何在不安装整个 WTP 包的情况下将 Tomcat 8 添加到 Eclipse Kepler 2022-01-01
- 如何强制对超级方法进行多态调用? 2022-01-01
- 如何对 HashSet 进行排序? 2022-01-01
- 首次使用 Hadoop,MapReduce Job 不运行 Reduce Phase 2022-01-01
- Spring Boot Freemarker从2.2.0升级失败 2022-01-01